This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

USB-CDC

Hello all

I am Raju Kamal, a Student from University of offenburg, Germany. Now I am faceing a problem to implement the USB-CDC protocal by using MAX3420e interface with our Microprocessor.
Can any body send me the c source code for MAX3420e for USB-CDC.
It will be gratefull from me!!!

Best regards
Raju Kamal

Parents
  • "Can any body send me the (sic) c source code for MAX3420e for USB-CDC"

    You are making the assumption that there is only 1 possible "source code" in the whole world to do this for any & every application. Unfortunately, this is not the case - otherwise Maxim could supply it with their chip!

    You need to study the MAX3420e datasheet - that will tell you what you need to do in order to use the chip.

    You should also visit the Maxim website and look there for examples, application notes, etc...

    This is the standard process for interfacing anything to anything else - see: www.8052.com/.../160143

Reply
  • "Can any body send me the (sic) c source code for MAX3420e for USB-CDC"

    You are making the assumption that there is only 1 possible "source code" in the whole world to do this for any & every application. Unfortunately, this is not the case - otherwise Maxim could supply it with their chip!

    You need to study the MAX3420e datasheet - that will tell you what you need to do in order to use the chip.

    You should also visit the Maxim website and look there for examples, application notes, etc...

    This is the standard process for interfacing anything to anything else - see: www.8052.com/.../160143

Children
  • Thanks Neil for sending the link for interface.
    May be i confuse you, actually i wish to see a source code as an example, which will be usefull for me to get some information and can program my project.

  • I have finished my program for USB-CDC with some problem.
    my problem is now i can read but cannot write. Is it like can communicate from Host to usb but cannot usb to host? Does anybody has any idea about this problem?

  • How do you expect anyone to make any comment on your program without seeing your program?

    It is like saying, "My car doesn't work - what's wrong with it"

    Remember: nobody knows anything about you, your project, or your code apart from what you provide in your posts!

  • ok, i am sending my code with couple of pages:
    #include <io.h>
    #include <string.h>
    #include "SD_driver.h"
    #include "FAT.h"
    #include "MAX3420E_BF1.h" // MAX3420E registers (rREGNAME), bits (bmBITNAME), and subroutine-definitions

    //Hauptprogramm
    int main()
    { long int g; int i; int msec_timer=0; int PC_DTR=0; int USB_int=0;

    // Enumeration, Initialisierung des internen FPGA-USB-Controllers ////////// for(g=0;g<4000000;g++); putport(0x13,4); for(g=0;g<3000000;g++); putport(0x13,0); for(g=0;g<3000000;g++); //Warte bis USB bereit! //////////////////////////////////////////////////////////////////////////// // Enumeration, Initialisierung des USB-Maxim3420E-Controllers ///////////// initialize_MAX(); // Enumeration-Interrupt abwarten for(g=0;g<3000000;g++); //Warte bis MaxUSB enumeriert ist

    USB_writeln(_Copyright); //Ausgabe der Versionsnummer

    if(loadData()!=0) USB_writeln("Karte nicht lesbar!\r\n\0"); while(1) //Endlosschleife der Befehlzeile { USB_writeln("\r\nSD\0"); USB_writeln(_path); //Aktueller Pfad USB_writeln(">\0");

    MaxUSB_readln(_stinp); //Befehl einlesen USB_writeln("\r\n\0"); USB_writeln2(" juhu\r\n\0");

    if((getport(0x16)&1)!=0) //SD-Karte gesteckt? Nein -> Meldung USB_writeln("Keine Karte vorhanden!\r\n\0"); else if(checkState()!=0) //SD-Karte initialisiert? { if(loadData()!=0) USB_writeln("Karte nicht lesbar!\r\n\0"); } else { for(i=0;_stinp[i]!='\0';i++)//Eingabe in Großbuchstaben wandeln if(_stinp[i]>0x60&&_stinp[i]<0x7B) _stinp[i]-=0x20;

    if(runProc(_stinp)!=0) //Auswertung der Befehlszeile

    USB_writeln("Befehl oder Dateiname nicht gefunden\r\n\0"); }

    } return 0;
    }

    // USB-Maxim3420E Routinen
    #include "EnumApp_enum_data.h" //CDC enumeration data
    #include "USB_SPI_COM.c"
    #include "USB_INIT.c"
    #include "USB_Enumeration.c"
    //#include "USB_Interrupt_handle.c"
    #include "USB_CDC_Appl.c"
    // SD-Karte bzw. Dateisystemroutinen
    #include "SD_driver.c"
    #include "FAT.c"

  • Now why did you post your code without specifying that it was code?

    Look once more at the information you see when posting comments - there is one sentence specifically mentioning what you should do when posting code. If you don't follow that instruction, the code you paste will be practically unreadable.

  • // basic function call that handles a SETUP transfer request.
    // The main loop calls this function whenever the MAX3420E asserts the SUDAVIRQ bit.
    void _USBmax3420E_ENUM(void)
    { readbytes(rSUDFIFO,9,SUD); // got a SETUP packet. Read 8 SETUP bytes

    switch(SUD[bmRequestType]&0x60) // Parse the SETUP packet. For request type, look only at b6&b5 { case 0x00: std_request(); break; case 0x20: class_request(); break; // just a stub/placeholder in this program // case 0x40: vendor_request(); break; // just a stub/placeholder in this program default: STALL_EP0 // unrecognized request type // If no legal case value is found, the correct peripheral // response is to send the STALL handshake instead of // ACK or NAK to indicate that it failed to recognize the request. }
    }

    // Standard USB request
    void std_request(void)
    { BYTE a;

    switch(SUD[bRequest]) // bRequest byte of the SETUP data packet // The ‘SR_’ names in the switch statement correspond to the nomenclature // in Chapter 9 of the USB Specification, which defines the USB standard // requests and data formats. // The SET_FEATURE and CLEAR_FEATURE requests are served by a single feature() // function that takes an argument indicating which operation, set (1) or // clear (0), is required. The SET_ADDRESS request does nothing but set the // ACKSTAT bit by doing a dummy read to the REVISION register. This is // because the MAX3420E hardware automatically handles the Set_Address request. { case SR_GET_DESCRIPTOR: send_descriptor(); break; case SR_SET_INTERFACE: set_interface(); break; case SR_GET_INTERFACE: get_interface(); break; case SR_GET_CONFIGURATION: get_configuration(); break; case SR_SET_CONFIGURATION: set_configuration(); break; case SR_SET_ADDRESS: a= rregAS(rFNADDR); break; // discard return value default: STALL_EP0 //wreg(9,0x23); }
    }

    // ************************************************************************** //
    // ************************************************************************** //
    // About Descriptors
    // Our application uses the following USB descriptor types:
    // - Device
    // - Configuration
    // *Interface
    // - Endpoint
    // - String
    // - (Report)
    // The include file EnumApp_enum_data.h contains the various descriptors used to
    // give our peripheral device its personality. A USB device can have multiple
    // configurations and interfaces, but our application uses only one of each.
    // The descriptors in parenthesis above are unique to the HID class,and would
    // be omitted by a non-HID device.

    void send_descriptor(void)
    { WORD reqlen,sendlen,desclen; BYTE *pDdata; // pointer to ROM Descriptor data to send int send_ZLP=FALSE;
    //
    // NOTE This function assumes all descriptors are 64 or fewer bytes and can be sent in a single packet
    // The send_descriptor function uses two variables to determine the number of bytes
    // to send: the requested length, reqlen; and the actual descriptor length, desclen,
    // which it retrieves from the descriptor tables. The function starts by setting
    // desclen = 0. If desclen is still zero after all the descriptor-type checks are
    // complete, a valid descriptor type was not found and the function sends the STALL handshake.
    // The requested lengths are found in the wLengthL and wLengthH bytes of the SUD array.
    // After loading this 16-bit value into the reqlen variable, the function uses a
    // switch statement to check for various values of wValueH, which indicates the descriptor type.

    desclen = 0; // check for zero as error condition (no case statements satisfied) reqlen = SUD[wLengthL] + 256*SUD[wLengthH]; // 16-bit
    // showword(reqlen);

    switch (SUD[wValueH]) // wValueH is descriptor type { case GD_DEVICE: desclen = DD[0]; // descriptor length pDdata =(BYTE*) DD; break;

    case GD_CONFIGURATION: if(SUD[wLengthL] > CD[2]) desclen = CD[2]; // Config descriptor includes interface, header and ep descriptors (67 Bytes [0x0043]) else desclen = SUD[wLengthL];

    if(SUD[wLengthH]!=0) desclen = CD[2]; // wLengthH=1 (last byte) pDdata = (BYTE *) CD; break;

    case GD_STRING: desclen = strDesc[SUD[wValueL]][0]; // wValueL=string index, array[0] is the length pDdata =(BYTE*) strDesc[SUD[wValueL]]; // point to first array element break;
    case CS_INTERFACE:

    if(SUD[wIndexL]==0) // Interface Number=0. Del EndPoint 2 (interrupción), Communication { //if(SUD[wLengthL]>CD[9]) desclen = CD[9]; //else desclen = SUD[wLengthL]; pDdata = (BYTE *) &CD[9]; }

    else if (SUD[wIndexL]==1)// Interface Number=1. Del EndPoint 1 (bulk), Datos { //if(SUD[wLengthL]>CD[44]) desclen = CD[44]; //else desclen = SUD[wLengthL]; pDdata = (BYTE *) &CD[44]; } break;

    case GD_REPORT: desclen = CD[25]; pDdata = (BYTE*)RepD; break;

    } // end switch on descriptor type

  • sorry every body i send again from the first

    int main()
    {
        long int g;
        int i;
        int  msec_timer=0;
         int PC_DTR=0;
         int USB_int=0;
    
        // Enumeration, Initialisierung des internen FPGA-USB-Controllers //////////
        for(g=0;g<4000000;g++);
        putport(0x13,4);
        for(g=0;g<3000000;g++);
        putport(0x13,0);
        for(g=0;g<3000000;g++);          //Warte bis USB bereit!
        ////////////////////////////////////////////////////////////////////////////
    
    
        // Enumeration, Initialisierung des USB-Maxim3420E-Controllers /////////////
        initialize_MAX();
        // Enumeration-Interrupt abwarten
        for(g=0;g<3000000;g++);             //Warte bis MaxUSB enumeriert ist
    
        USB_writeln(_Copyright);         //Ausgabe der Versionsnummer
    
        if(loadData()!=0) USB_writeln("Karte nicht lesbar!\r\n\0");
        while(1)                        //Endlosschleife der Befehlzeile
      {
           USB_writeln("\r\nSD\0");
           USB_writeln(_path);          //Aktueller Pfad
           USB_writeln(">\0");
    //       USB_readln(_stinp);         //Befehl einlesen
    
           MaxUSB_readln(_stinp);
    
         //  USB_writeln(_stinp);
    
           USB_writeln("\r\n\0");
            USB_writeln2(" juhu\r\n\0");
    
    
           if((getport(0x16)&1)!=0)    //SD-Karte gesteckt? Nein -> Meldung
               USB_writeln("Keine Karte vorhanden!\r\n\0");
          else if(checkState()!=0)    //SD-Karte initialisiert?
          {   if(loadData()!=0) USB_writeln("Karte nicht lesbar!\r\n\0");   }
           else
           {   for(i=0;_stinp[i]!='\0';i++)//Eingabe in Großbuchstaben wandeln
                  if(_stinp[i]>0x60&&_stinp[i]<0x7B) _stinp[i]-=0x20;
    
               if(runProc(_stinp)!=0)         //Auswertung der Befehlszeile
    
            USB_writeln("Befehl oder Dateiname nicht gefunden\r\n\0");
            }
    
    
        }
        return 0;
    }
    

  • void _USBmax3420E_ENUM(void)
    {
     readbytes(rSUDFIFO,9,SUD);
           // got a SETUP packet. Read 8 SETUP bytes
    
    switch(SUD[bmRequestType]&0x60)     // Parse the SETUP packet. For request type, look only at b6&b5
        {
        case 0x00:  std_request();          break;
        case 0x20:  class_request();        break;  // just a stub/placeholder in this program
       // case 0x40:  vendor_request();       break;  // just a stub/placeholder in this program
        default:    STALL_EP0  // unrecognized request type
                               // If no legal case value is found, the correct peripheral
                               // response is to send the STALL handshake instead of
                               // ACK or NAK to indicate that it failed to recognize the request.
        }
    }
    
    
    // Standard USB request
    void std_request(void)
    {
      BYTE a;
    
      switch(SUD[bRequest])  // bRequest byte of the SETUP data packet
         // The ‘SR_’ names in the switch statement correspond to the nomenclature
         // in Chapter 9 of the USB Specification, which defines the USB standard
         // requests and data formats.
         // The SET_FEATURE and CLEAR_FEATURE requests are served by a single feature()
         // function that takes an argument indicating which operation, set (1) or
         // clear (0), is required. The SET_ADDRESS request does nothing but set the
         // ACKSTAT bit by doing a dummy read to the REVISION register. This is
         // because the MAX3420E hardware automatically handles the Set_Address request.
        {
         case SR_GET_DESCRIPTOR:      send_descriptor();    break;
         case SR_SET_INTERFACE:       set_interface();      break;
         case SR_GET_INTERFACE:       get_interface();      break;
         case SR_GET_CONFIGURATION:   get_configuration();  break;
         case SR_SET_CONFIGURATION:   set_configuration();  break;
         case SR_SET_ADDRESS:         a= rregAS(rFNADDR);   break;  // discard return value
         default:  STALL_EP0 //wreg(9,0x23);
         }
    }
    
    ************************************************************************** /
    // About Descriptors
    // Our application uses the following USB descriptor types:
    // - Device
    // - Configuration
    //   *Interface
    
    //     - Endpoint
    // - String
    // - (Report)
    // The include file EnumApp_enum_data.h contains the various descriptors used to
    // give our peripheral device its personality. A USB device can have multiple
    // configurations and interfaces, but our application uses only one of each.
    // The descriptors in parenthesis above are unique to the HID class,and would
    // be omitted by a non-HID device.
    
    void send_descriptor(void)
    {
      WORD reqlen,sendlen,desclen;
      BYTE *pDdata;                         // pointer to ROM Descriptor data to send
      int send_ZLP=FALSE;
    //
    // NOTE This function assumes all descriptors are 64 or fewer bytes and can be sent in a single packet
    // The send_descriptor function uses two variables to determine the number of bytes
    // to send: the requested length, reqlen; and the actual descriptor length, desclen,
    // which it retrieves from the descriptor tables. The function starts by setting
    // desclen = 0. If desclen is still zero after all the descriptor-type checks are
    // complete, a valid descriptor type was not found and the function sends the STALL handshake.
    
    // The requested lengths are found in the wLengthL and wLengthH bytes of the SUD array.
    // After loading this 16-bit value into the reqlen variable, the function uses a
    // switch statement to check for various values of wValueH, which indicates the descriptor type.
    
       desclen = 0;                                    // check for zero as error condition (no case statements satisfied)
       reqlen = SUD[wLengthL] + 256*SUD[wLengthH];     // 16-bit
    
            switch (SUD[wValueH])                      // wValueH is descriptor type
            {
            case  GD_DEVICE:
                  desclen = DD[0];  // descriptor length
                  pDdata =(BYTE*) DD;
                  break;
    
            case  GD_CONFIGURATION:
    
                 if(SUD[wLengthL] > CD[2])
                     desclen = CD[2];       // Config descriptor includes interface, header and ep descriptors (67 Bytes [0x0043])
                 else
                     desclen = SUD[wLengthL];
                 if(SUD[wLengthH]!=0)
                      desclen = CD[2];         // wLengthH=1 (last byte)
                      pDdata = (BYTE *) CD;
                  break;
    
            case  GD_STRING:
              desclen = strDesc[SUD[wValueL]][0];   // wValueL=string index, array[0] is the length
              pDdata =(BYTE*) strDesc[SUD[wValueL]];       // point to first array element
              break;
    
             case CS_INTERFACE:
    if(SUD[wIndexL]==0)    // Interface Number=0. Del EndPoint 2 (interrupción), Communication
                             {
                                    //if(SUD[wLengthL]>CD[9])
                                    desclen = CD[9];
                                    //else desclen = SUD[wLengthL];
                                    pDdata = (BYTE *) &CD[9];
                             }
                             else if (SUD[wIndexL]==1)      // Interface Number=1. Del EndPoint 1 (bulk), Datos
                             {
                                    //if(SUD[wLengthL]>CD[44])
                                     desclen = CD[44];
                                    //else desclen = SUD[wLengthL];
                                    pDdata = (BYTE *) &CD[44];
                             }
                                    break;
    
    
    case  GD_REPORT:
                  desclen = CD[25];
                  pDdata = (BYTE*)RepD;
            break;
    
    
            }       // end switch on descriptor type
    
    

  • 
    ///////////// Send out the Enumeration data to the bus /////////////////////////
            if (desclen!=0)                          // one of the case statements above filled in a value
            {
                    sendlen = desclen;                      // Send Lower data
                    if((desclen % 64) == 0) send_ZLP=TRUE;  // Flag to send ZLP
                    while(desclen > 0)
                    {
                            if (desclen>64)
                              sendlen=64;   // if packet>64 bytes
                            else
                              sendlen=desclen;           // if packet<=64 bytes
    
                            while(!(rreg(rEPIRQ) & bmIN0BAVIRQ)); // Waiting for Enumeration-FIFO While out buff. isn't free
                          //   USB_writeln("\n\r\0");
                             writebytes(rEP0FIFO,sendlen,pDdata);// Write data in FIFO (EP_CONTROL)
                              pDdata=(pDdata+sendlen);
    
                              if (desclen < 64)
                                 wregAS(rEP0BC,sendlen);    // load EP0BC to arm the EP0-IN transfer & ACKSTAT
                              else
                                 wreg(rEP0BC,sendlen);      // load EP0BC to arm the EP0-IN transfer & ACKSTAT
                                 desclen-=sendlen;          // Resta los datos ya enviados
                    }
                    if(send_ZLP)
                       wregAS(rEP0BC,0);                    // load EP0BC to arm the EP0-IN transfer & ACKSTAT
            }
            else STALL_EP0;  // none of the descriptor types match
    }
    // ************************************************************************** //
    // ************************************************************************** //
    // FUNCTION: Set/Get_Feature. Call as feature(1) for Set_Feature or feature(0) for Clear_Feature.
    // There are two set/clear feature requests:
    //      To a DEVICE:    Remote Wakeup (RWU).
    //      To an ENDPOINT: Stall (EP3 only for this app)
    //
    void feature(BYTE sc)
    {
    int b;
    BYTE mask,a;
      if((SUD[bmRequestType]==0x02) // dir=h->p, recipient = ENDPOINT
      &&  (SUD[wValueL]==0x00)      // wValueL is feature selector, 00 is EP Halt
      &&  (SUD[wIndexL]==0x83))     // wIndexL is endpoint number IN3=83
          {
          mask=rreg(rEPSTALLS);   // read existing bits
          if(sc==1)               // set_feature
            {
            mask += bmSTLEP3IN;       // Halt EP3IN
            ep3stall=1;
            }
          else                        // clear_feature
            {
          //  mask &= ~bmSTLEP3IN;      // UnHalt EP3IN
             b = ~bmSTLEP3IN;
             mask &=b;
    
            ep3stall=0;
            wreg(rCLRTOGS,bmCTGEP3IN);  // clear the EP3 data toggle
            }
          wreg(rEPSTALLS,(mask|bmACKSTAT)); // Don't use wregAS for this--directly writing the ACKSTAT bit
          }
      else if ((SUD[bmRequestType]==0x00)   // dir=h->p, recipient = DEVICE
               &&  (SUD[wValueL]==0x01))    // wValueL is feature selector, 01 is Device_Remote_Wakeup
                {
                RWU_enabled = sc<<1;        // =2 for set, =0 for clear feature. The shift puts it in the get_status bit position.
                a=rregAS(rFNADDR);            // dummy read to set ACKSTAT
                }
      else STALL_EP0
    }
    
    ************************************************************************** //
    // The get_status function in Figure 19 first decodes that portion of the USB
    // peripheral to which the request is directed: device, interface, or endpoint.
    void get_status(void)
    {
    BYTE testbyte;
    testbyte=SUD[bmRequestType];
    switch(testbyte)
            {
            case 0x80:                      // directed to DEVICE
                    wreg(rEP0FIFO,(RWU_enabled+1)); // first byte is 000000rs where r=enabled for RWU and s=self-powered.
                    wreg(rEP0FIFO,0x00);            // second byte is always 0
                    wregAS(rEP0BC,2);               // load byte count, arm the IN transfer, ACK the status stage of the CTL transfer
                    break;
            case 0x81:                      // directed to INTERFACE
                    wreg(rEP0FIFO,0x00);            // this one is easy--two zero bytes
                    wreg(rEP0FIFO,0x00);
                    wregAS(rEP0BC,2);               // load byte count, arm the IN transfer, ACK the status stage of the CTL transfer
                    break;
            case 0x82:                      // directed to ENDPOINT
                    if(SUD[wIndexL]==0x83)          // We only reported ep3, so it's the only one the host can stall IN3=83
                      {
                      wreg(rEP0FIFO,ep3stall);      // first byte is 0000000h where h is the halt (stall) bit
                      wreg(rEP0FIFO,0x00);          // second byte is always 0
                      wregAS(rEP0BC,2);             // load byte count, arm the IN transfer, ACK the status stage of the CTL transfer
                      break;
                      }
                    else  STALL_EP0         // Host tried to stall an invalid endpoint (not 3)
            default:      STALL_EP0         // don't recognize the request
            }
    }
    
    / ************************************************************************** //
    void set_interface(void)        // All we accept are Interface=0 and AlternateSetting=0, otherwise send STALL
    {
    BYTE dumval;
    if((SUD[wValueL]==0)            // wValueL=Alternate Setting index
      &&(SUD[wIndexL]==0))          // wIndexL=Interface index
            dumval=rregAS(rFNADDR); // dummy read to set the ACKSTAT bit
    else STALL_EP0
    }
    
    // ************************************************************************** //
    void get_interface(void)        // Check for Interface=0, always report AlternateSetting=0
    {
    if(SUD[wIndexL]==0)             // wIndexL=Interface index
      {
      wreg(rEP0FIFO,0);             // AS=0
      wregAS(rEP0BC,1);             // send one byte, ACKSTAT
      }
    else STALL_EP0
    }
    
    **************************************************************************
    void set_configuration(void)
    {BYTE a;
    configval=SUD[wValueL];           // Store the config value
    if(configval != 0)                // If we are configured,
      SETBIT(rUSBIEN,bmSUSPIE);       // start looking for SUSPEND interrupts
    a=rregAS(rFNADDR);                  // dummy read to set the ACKSTAT bit
    }
    
    void get_configuration(void)
    {
    wreg(rEP0FIFO,configval);         // Send the config value
    wregAS(rEP0BC,1);
    }
    
    

  • ************************************************************************** //
    void class_request(void)
    
    {
            switch (SUD[bRequest])
            {
            case SEND_ENCAPSULATED_COMMAND: wregAS(rEP0BC, 0);      break; // send_encapsulated_command();  break;
            case GET_ENCAPSULATED_RESPONSE: wregAS(rEP0BC, 0);      break; // send_encapsulated_command();  break; // get_encapsulated_response();  break;
    
            case SET_COMM_FEATURE:  break;
            case GET_COMM_FEATURE:  break;
            case CLEAR_COMM_FEATURE:break;
            case SET_LINE_CONDING:
            {
                    wregAS(rEP0BC, 0);                              // Envía un paquete de longitud 0 para la etapa de 'STATUS' (?)
                    if(SUD[wLengthL]>0)
                    {
                            while(!(rreg(rEPIRQ) & bmOUT0DAVIRQ) && SUD[7]<=5) SUD[7]++;
            readbytes(rEP0FIFO,SUD[wLengthL],(unsigned char *)&SUD[0]);               // Lee la configuración serie por el EP0 (hay que cambiar algo para que lea?)
                    }
            } break;
            case GET_LINE_CODING:
            {
                    wregAS(rEP0BC, 0);                              // Envía un paquete de longitud 0 para la etapa de 'STATUS' (?)
            writebytes(rEP0FIFO,SUD[wLengthL],(unsigned char *)&SerialConf[0]);
                    wreg(rEP0BC, SUD[wLengthL]);
            } break;
            case SET_CONTROL_LINE_STATE:
            {
                    if(configval)
                    {
                            USB_init=1;                                     // Si llega a este punto, el dispositivo ha terminado de inicializarse
                            if((SUD[wValueL]&0x01)==0x01)// PC listo para aceptar tramas del AZC
                                    PC_DTR=1;
                            if(SUD[wValueL]==0x00)          // Se ha cortado la comunicación con el PC
                                    PC_DTR=0;
                    }
                    wregAS(rEP3INBC, 0);
            } break;
            case SEND_BREAK:        break;
            default: STALL_EP0;                                     // none of the descriptor types match
            }
    }
    
    
    void vendor_request(void)
    {
    STALL_EP0;
    }
    

  • // Intialisation from the USB-Maxim3420E-Controller
    
    void initialize_MAX(void)
    {
    BYTE rd;
    int int_mask;
    
    // software flags
    configval=0;                  // at pwr on OR bus reset we're unconfigured
    Suspended=0;
    RWU_enabled=0;                // Set by host Set_Feature(enable RWU) request
    
    
    // Mask out of the USB-Maxim-Interrupt in the Interruptcontroller of the SIRIUS-System
    // USB-Interrupt-Position in SIRIUS-System: Bit 7
     int_mask= ((getport(0x23)) & 0xBF);
     putport (0x23, int_mask);
    
    // Always set the FDUPSPI bit in the PINCTL register FIRST if you are using the SPI port in
    // full duplex mode. This configures the port properly for subsequent SPI accesses.
    // Fullduplex means SPI with Data-In and Data-Out wires
    // INTLEVEL=0 --> Edge-Interrupts ; INTLEVEL=1 --> Level-Interrupts
    // POSINT=0 --> 1-0 transition for interrupts  ; POSINT=1 --> 0-1 transition for interrupts
    //------------------------------------------------------------------------------
    // PINCTL-Register:
    // | EP3INAK | EP2INAK | EP0INAK | FDUPSPI | INTLEVEL | POSINT | GPXB | GPXA |
    //------------------------------------------------------------------------------
    //wreg(rPINCTL,(bmFDUPSPI+bmPOSINT+gpxSOF)); // (17h) MAX3420: SPI=full-duplex, INT=from 0 to 1 for interrupt, GPX=SOF
    
     wreg(rPINCTL,0x13); // MAX3420: SPI=full-duplex, INTLEVEL=0(edge-ints), POSINT=0 --> 1-0 interrupts, GPX=SOF
      // DEBUG
      //rd = rreg(rPINCTL);
      //showbyte(rd);
    
    
    // Maxim-USB-Chip reset to initial conditions
     Reset_MAX();
    
    // This is a self-powered design, so the host could turn off Vbus while we are powered.
    // Therefore set the VBGATE bit to have the MAX3420E automatically disconnect the D+
    // pullup resistor in the absense of Vbus. Note: the VBCOMP pin must be connected to Vbus
    // or pulled high for this code to work--a low on VBCOMP will prevent USB connection.
    
     wreg(rUSBCTL,(bmCONNECT+bmVBGATE)); // VBGATE=1 disconnects D+ pullup if host turns off VBUS
    
    // In SIRIUS-System the Interrupt line is inverted !!
    // For a POSINT=0 -> 1-0 transistion --> inverter in SIRIUS-System
    // --> Interrupt-Edge-Register must be programmed to 0-1 transition means high active
     int_mask= ((getport(0x22)) | 0x40);
     putport (0x22, int_mask);
    
     //ENABLE_IRQS
     //wreg(rEPIEN,0x34);  //bmSUDAVIE+bmIN3BAVIE+bmOUT1DAVIE = 110100b =64hex
     wreg(rEPIEN,0x3C);  //bmSUDAVIE+bmIN3BAVIE+bmIN2BAVIE+bmOUT1DAVIE = 0011 1100b =3Chex
    
     wreg(rUSBIEN,(bmURESIE+bmURESDNIE));
     wreg(rCPUCTL,bmIE);                 // Enable the INT pin
    
    // Enbling the USB-Maxim-Interruptbit in the SIRIUS-Interrupcontroller
     int_mask= ((getport(0x23)) | 0x40);
     //int_mask = getport(0x23);
     //int_mask = int_mask | 0x40;
     putport (0x23, int_mask);
    }
    
    // Reset Routine welche den Max-Chip zurücksetzt.
    void Reset_MAX(void)
    {
    BYTE dum;
    wreg(rUSBCTL,0x20);     // chip reset
    wreg(rUSBCTL,0x00);     // remove the reset
        do                  // Chip reset stops the oscillator. Wait for it to stabilize.
        {
        dum=rreg(rUSBIRQ);
        dum &= bmOSCOKIRQ;
        }
        while (dum==0);
    }
    

  • 
    // Possible Interrupts for our application:
    // a. Setup Data arrived (SUDAVIRQ).
    // b. The host requested keyboard data by sending a data request to EP3-IN.
    // c. The host suspended the bus by stopping traffic for three milliseconds.
    // d. The host initiated a bus reset.
    // e. The host completed bus reset signaling.
    
    // Poll the Interrupt line from the USB-Max-Chip
    // --> Later it should work automtically in a Interrupt-Service-Routine
    //BYTE MAX_Int_Pending(void)
    //{
    //return (BYTE)((USB_CYPRESSFLAG&0x01)==1); //  USB_Cypressflag=1 --> true
    //}
    
    
    // *********************************** //
    // Interrupt Service Requests
    // *********************************** //
    // This function checks 4 IRQ bits
    // 1. bmSUDAVIRQ A SETUP packet arrived.
    // The host controls a device by sending SETUP packets.
    // 2. bmIN3BAVIRQ The host asked for another data packet from the HID keyboard.
    // It uses endpoint 3-IN for this request. BAV means Buffer Available.
    // 3. bmURESIRQ The host started signaling a bus reset.
    // 4. bmUSBRESDNIRQ The host finished signaling a bus reset
    //void _service_irqs(void)
    void _service_irqs(void)
    {
    // Read out the two IRQ-Register and save the result in variables
    BYTE itest1,itest2;
    
    itest1 = rreg(rEPIRQ);            // Check the EPIRQ bits
    itest2 = rreg(rUSBIRQ);           // Check the USBIRQ bits
    
    
    //  // Debug it
    //  beep(45,46); // Debug-AHI-Ton
    //  USB_writeln("itest1=");
    //  showByte(itest1);
    //  USB_writeln("itest2=");
    //  showByte(itest2);
    //  USB_writeln("\n\r\0");
    
    if(itest1 & bmSUDAVIRQ)           // Check for SETUP data
        {
         //  beep(45,46); // Debug-AHI-Ton
         wreg(rEPIRQ,bmSUDAVIRQ);     // clear the SUDAV IRQ
        _USBmax3420E_ENUM();
        }
    if(itest1 & bmIN3BAVIRQ)          // Was an EP3-IN packet just dispatched to the host?
        {
     //   do_IN3();                     // Yes--load another keystroke and arm the endpoint
        }                             // NOTE: don't clear the IN3BAVIRQ bit here--loading the EP3-IN byte
                                      // count register in the do_IN3() function does it.
    
    if((configval != 0) && (itest2&bmSUSPIRQ))   // HOST suspended bus for 3 msec
        {
        wreg(rUSBIRQ,(bmSUSPIRQ+bmBUSACTIRQ));  // clear the IRQ and bus activity IRQ
    //    L2_ON                         // turn on the SUSPEND light
    //    L3_OFF                        // turn off blinking light (in case it's on)
        Suspended=1;                  // signal the main loop
        }
    
    
    // The last two checks handle USB bus reset. These code sections clear the
    // IRQ bits and turn a bus reset light on and off. Note that MAX3420E code
    // should always include a test for a USB bus reset. This is because the
    // MAX3420E clears most of its interrupt enable register bits during a USB bus
    // reset. Therefore, the code should be alert to a bus reset. When the reset is
    // complete (signaled by the USBRESDN IRQ), it should re-enable the interrupts
    // that it is using for the application.
    
    if(rreg(rUSBIRQ)& bmURESIRQ)
        {
    //    USB_writeln("Clear URESIRQ\n\0");
        wreg(rUSBIRQ,bmURESIRQ);      // clear the IRQ
        }
    if(rreg(rUSBIRQ) & bmURESDNIRQ)
        {
    //    USB_writeln("Clear URESDNIRQ\n\0");
        wreg(rUSBIRQ,bmURESDNIRQ);    // clear the IRQ bit
    //    Suspended=0;                  // in case we were suspended
        //ENABLE_IRQS                   // ...because a bus reset clears the IE bits
         wreg(rEPIEN,(bmSUDAVIE+bmIN3BAVIE));
         wreg(rUSBIEN,(bmURESIE+bmURESDNIE));
        }
    }
    

  • // ********************************************************* //
    // ****************** SPI - Routinen *********************** //
    // ********************************************************* //
    // ------------------------------------------------------------
    // The code below customizes this app for the SIRIUS-uC-System
    // microprocessor and the Rowley compiler. Only this
    // section changes if you use a different uP and/or compiler.
    // ------------------------------------------------------------
    // ************************************************************************** //
    // First byte of every SPI transfer is a command byte like following format:
    // ----------------------------------------
    // | b7 | b6 | b5 | b4 | b3 | b2 | b1 | b0 |
    // ----------------------------------------
    // |Reg4|Reg3|Reg2|Reg1|Reg0|  0 |DIR |ACK |
    // ----------------------------------------
    // Bit7 to 3 = Register Address
    // Bit1 = Direction (DIR=0=Read ; DIR=1=Write)
    // Bit0 = ACKSTAT bit in R9
    // ************************************************************************** //
    
    
    // Liest ueber den SPI-Bus ein Register des Max-USB-Chips aus
    BYTE rreg(BYTE reg)
    {
      BYTE dum;
    
    //    putport(0x3E, 0x66);
    
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // Set CS2=0
      writeSPI(reg);                         // Set on USB-Max-Chip the reg number w. dir=0 (IN)
      dum = readSPI();                       // Read the register value
      putport(SPI_SIRIUS_PORT_STEUER,0x07);  // Set CS2=1
      return(dum);
    }
    
    
    // Schreibt ueber den SPI-Bus ein Register des Max-USB-Chips
    void wreg(BYTE reg, BYTE dat)
    {
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // 0000_0011 --> Mode0 , CS2=0
      reg = reg+2;                           // Write-Bit = +2
      writeSPI(reg);                         // Send the register-number with the DIR bit (b1) set to WRITE
      writeSPI(dat);                         // Send the data to the register
      putport(SPI_SIRIUS_PORT_STEUER,0x07);  // Set CS2 high
    }
    
    
    // Liest ueber den SPI-Bus ein Register des Max-USB-Chips aus.
    // Das ACKSTAT-Bit wird im Commando-Byte gesetzt
    BYTE rregAS(BYTE reg)
    {
    BYTE dum;
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // Set CS2=0
      writeSPI(reg+1);                       // Reg number with dir=0 (IN) and ACKSTAT=1
      dum = readSPI();                       // Read the register value
      putport(SPI_SIRIUS_PORT_STEUER,0x07);  // Set CS2=1
      return(dum);
    }
    
    
    // Schreibt ueber den SPI-Bus ein Register des Max-USB-Chips
    void wregAS(BYTE reg, BYTE dat)
    {
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // 0000_0011 --> Mode0 , CS2=0
       reg = reg+3;                          // Write-Bit und Ack-Bit = +3
      writeSPI(reg);                         // Reg number with DIR=1 (write) and ACKSTAT=1
      writeSPI(dat);                         // Send the data to the register
      putport(SPI_SIRIUS_PORT_STEUER,0x07) ; // Set CS2 high
    }
    
    
    // Liest N-Bytes ueber den SPI-Bus eines Register des Max-USB-Chips aus.
    void readbytes(BYTE reg, BYTE N, BYTE *p)
    {
      BYTE j;
    
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // 0000_0011 --> Mode0 , CS2=0
      writeSPI(reg);                         // Write-Bit b1=0 to command a read operation
    
      // Read-Loop
      for(j=0; j<N; j++)
        {
         *p = readSPI();                     // Store it in the data array
         p++;                                // Bump the pointer
        }
      putport(SPI_SIRIUS_PORT_STEUER,0x07);  // Set CS2 high
    }
    
    
    // Schreibt N-Bytes ueber den SPI-Bus eines Register des Max-USB-Chips.
    void writebytes(BYTE reg, BYTE N, BYTE *p)
    {
      BYTE j,wd;
    
      putport(SPI_SIRIUS_PORT_STEUER,0x03);  // 0000_0011 --> Mode0 , CS2=0
      writeSPI( reg+2);                      // write bit b1=1 to command a write operation
    
      // Writes N Bytes
      for(j=0; j<N; j++)
        {
        wd = *p;                             // write the array value
    
      //  showbyte(wd);
    
        writeSPI(wd);                        // write the byte from the array position
        p++;                                 // Bump the pointer
        }
      putport(SPI_SIRIUS_PORT_STEUER,0x07);  // Set CS2 high
    }
    
    
    
    
    // Zeigt ueber den intern FPGA-integrierten USB-Controller ein Byte im USB-COM an
    void showByte(char Byte)
    {   int i;
        char x;
        char *e={"00\0"};
        for(i=1;i>=0;i--)
        {   x=(Byte&0xF);
            Byte=Byte>>4;
            if(x<10) e[i]=x+0x30;
            else e[i]=x+0x41-10;
        }
        USB_writeln(e);
    }
    
    //Word in HEX ausgeben
    void showword(U16 Word)
    {   int i;
        U08 x;
        char *e={"0000\0"};
        for(i=3;i>=0;i--)
        {   x=(Word&0xF);
            Word=Word>>4;
            if(x<10) e[i]=x+0x30;
            else e[i]=x+0x41-10;
        }
        USB_writeln(e);
    }
    
     void check_for_resume(void)
    {
          //  SPI_ini(0);
           // USB_CSE;
             putport(SPI_SIRIUS_PORT_STEUER,0x03);
            if(rreg(rUSBIRQ) & bmBUSACTIRQ)     // THE HOST RESUMED BUS TRAFFIC
                    Suspended=0;                    // no longer suspended
          //  USB_CSD;
           putport(SPI_SIRIUS_PORT_STEUER,0x07);
    }
    

  • void USB_writeln2(char *name)
    {
       int g;
    
    //  namelength = sizeof(name);     // so we can check for the end of the message
    //  showByte(namelength);
    
    //   while(USB_Max_EP3_flag==0) {}   // wait for an interrupt which set the flag
    
           //beep(0x55,0x55);
    
            for(g=0; g < 64; g++)
             {
                 //  USB_writeln("test");
                   if (name[g]==0)             // Strings are 0 terminated
                    //wreg( rEP1OUTFIFO,0);      // Rest of the bytes are 0
                     wreg(rEP2INFIFO,0);
                   else
                   //wreg(rEP1OUTFIFO,name[g]);
                    wreg(rEP2INFIFO,name[g]);  // Load the string (64 times)
                   // wreg( rEP1OUTFIFO,0x2);
             }
               wreg(rEP2INBC,64);
    
           //  wreg( rEP1OUTBC,64);
    
    

  • First i would like to say sorry because of some miscommunication and some bad posting.
    Now whatever i have send is my code, some of them i have found from this forum and some from maxim. As well as i also need to change some to compatible with our compiler.

    So Now i am faceing a problem for writing by the usb.
    For my project i need to use the hyperterminal com. for coummincation i am using Docklight Scripting software. the final position is now if i send any data by the docklight or windows hyperterminal, it shows me transfer data but does not show receiving data.
    If it is still confuse please inform me i will try to explain it more.