//IRman protocol: respond to IR with OK... void IRmanString(void){ if( mUSBUSARTIsTxTrfReady() ){ //it's always ready, but this could be done better irToy.usbOut[0]='O';//answer OK irToy.usbOut[1]='K'; putUnsignedCharArrayUsbUsart(irToy.usbOut,2); } }
void sendok(void){ unsigned char b[2]; if( mUSBUSARTIsTxTrfReady() ){ //it's always ready, but this could be done better b[0]='1';//answer OK putUnsignedCharArrayUsbUsart(b,1); } }
void send(unsigned char c){ unsigned char b[2]; if( mUSBUSARTIsTxTrfReady() ){ //it's always ready, but this could be done better b[0]=c; putUnsignedCharArrayUsbUsart(b,1); } }
//setup for USB UART void Usb2UartSetup(void){ if(mUSBUSARTIsTxTrfReady()) { irToy.usbOut[0]='U';//answer OK irToy.usbOut[1]='0'; irToy.usbOut[2]='1'; putUnsignedCharArrayUsbUsart(irToy.usbOut,3); } Sm_Usb_Uart=SM_USB_UART_CONFIG_MODE; Configbuffctr=0; }
//IR signals are first captured in the interrupt loop below //when the capture is complete, the bits are decoded into bytes and sent to USB from this function void ProcessIR(void){ static unsigned char i; if((decoderState==SEND) && (USBUSARTIsTxTrfReady())){ //process IR data (decode RC5) in irToy.s[] //byte# | description //0 second start bit, use as bit 6 in command byte for RC5x protocol support //1 toggle bit, discard //2-6 5bit address //7-12 6bit command //final USB packet is: //byte 1 bits 7-5 (don't care) //byte 1 bits 4-0 (5 address bits) //byte 2 bit 7 (don't care) //byte 2 bit 6 (RC5x/start bit 2, not inversed) //byte 2 bits 5-0 (RC5 6 bit command) //byte 3-6 (unused) //first byte of USB data is the RC5 address (lower 5 bits of first byte) //loop through irToy.s[] and shift the 5bit address into the USB output buffer //5 address bits, 5-0, MSB first irToy.usbOut[0]=0; //clear USB buffer byte to 0 for(i=2;i<7;i++){ //loop through and assemble 5 address bits into a byte, bit 4 to bit 0, MSB first irToy.usbOut[0]<<=1; //shift last bit up irToy.usbOut[0]|=irToy.s[i]; //set bit 0 to value of irToy.s[i] } //second byte of USB data is the RC5 command (lower 6 or 7 bits of second byte) //for RC5x, the second start bit is used as the MSB of the command (bit 6) irToy.usbOut[1]=irToy.s[0]; //start with the value of the RC5x bit (bit 6), //irToy.usbOut[1]=(~irToy.s[0]); //technically this should be inversed, but that would ruin compatibility for exisitng remote profiles //loop through irToy.s[] and shift the 'normal' 6 command bits, bit 5 to bit 0, into the USB output buffer //6 command bits, 5-0, MSB first for(i=7;i<13;i++){ //loop through and assemble 6 command bits into a byte, bit 5 to bit 0, MSB first irToy.usbOut[1]<<=1; //shift last bit up irToy.usbOut[1]|=irToy.s[i]; //set bit 0 to value of irToy.s[i] } irToy.usbOut[2]=0x00;//four extra bytes for 6 byte IRMAN format irToy.usbOut[3]=0x00; irToy.usbOut[4]=0x00; irToy.usbOut[5]=0x00; putUnsignedCharArrayUsbUsart(irToy.usbOut,6); decoderState=IDLE;//wait for more RC commands.... IRRX_IE=1;//interrupts back on } }
unsigned char SUMPlogicService(void){ static unsigned char i, USBWriteCount; switch(LAstate){//dump data //case IDLE: //case ARMED: //case LA_START_DUMP: case LA_DUMP: if(USBUSARTIsTxTrfReady()){ USBWriteCount=0; for(i=0; i<8; i++){ loga.btrack<<=1; //shift bit at begin to reset from last loop if((loga.btrack==0) && (loga.ptr>0) ){//no bits left loga.btrack=0b00000001;//start at bit 0 loga.ptr--; } if( (irToy.s[loga.ptr] & loga.btrack)!=0) irToy.usbOut[USBWriteCount]=0; else irToy.usbOut[USBWriteCount]=1; USBWriteCount++; loga.sample--; if(loga.sample==0){//send 64/128/512/1024 samples exactly! LAstate=LA_RESET; break; } } putUnsignedCharArrayUsbUsart(irToy.usbOut,USBWriteCount); } break; case LA_RESET: LAstate = LA_IDLE; return 0xff; break; } return 0; }
void SUMPlogicCommand(unsigned char inByte){ static enum _SUMP { C_IDLE = 0, C_PARAMETERS, C_PROCESS, } sumpRXstate = C_IDLE; static struct _sumpRX { unsigned char command[5]; unsigned char parameters; unsigned char parCnt; } sumpRX; switch(sumpRXstate){ //this is a state machine that grabs the incoming commands one byte at a time case C_IDLE: switch(inByte){//switch on the current byte case SUMP_RESET://reset T2IE=0; //disable interrupts... T2ON=0;//tmr2 off IRRX_IE = 0; //DISABLE RB port change interrupt LAstate=LA_RESET; break; case SUMP_ID://SLA0 or 1 backwards: 1ALS if( mUSBUSARTIsTxTrfReady() ){ //putsUSBUSART("1ALS"); //doesn't work b/c of 0x00 irToy.usbOut[0]='1'; irToy.usbOut[1]='A'; irToy.usbOut[2]='L'; irToy.usbOut[3]='S'; putUnsignedCharArrayUsbUsart(irToy.usbOut,4); } break; case SUMP_RUN://arm the triger LED_LAT |= LED_PIN;//ARMED, turn on LED LAstate=LA_ARMED; IRRX_IF = 0; //Reset the RB Port Change Interrupt Flag bit IRRX_IE = 1; //Enables the RB port change interrupt break; case SUMP_XON://resume send data // xflow=1; break; case SUMP_XOFF://pause send data // xflow=0; break; default://long command sumpRX.command[0]=inByte;//store first command byte sumpRX.parameters=4; //all long commands are 5 bytes, get 4 parameters sumpRX.parCnt=0;//reset the parameter counter sumpRXstate=C_PARAMETERS; break; } break; case C_PARAMETERS: sumpRX.command[sumpRX.parCnt]=inByte;//store each parameter sumpRX.parCnt++; if(sumpRX.parCnt<sumpRX.parameters) break; //if not all parameters, quit case C_PROCESS: //ignore all long commands for now sumpRXstate=C_IDLE; break; } }
void main(void) { unsigned char c,x,y,led; unsigned long l; // Default all pins to digital ADCON1 |= 0x0F; // Disable USB external transceiver to allow RB1/RB2 UCFGbits.UTRDIS = 0; // set pin to output TRISBbits.TRISB0 = 0; TRISBbits.TRISB1 = 0; TRISBbits.TRISB2 = 0; TRISBbits.TRISB3 = 0; LED0 = 1; LED1 = LED2 = LED3 = 0; // TODO: Remove magic with macro usb_init(cdc_device_descriptor, cdc_config_descriptor, cdc_str_descs, USB_NUM_STRINGS); usb_start(); initCDC(); usbbufflush(); do { if (!TestUsbInterruptEnabled()) USBDeviceTasks(); switch(usb_device_state){ case DETACHED_STATE: LED1 = 0; LED2 = 0; LED3 = 0; case ATTACHED_STATE: LED1 = 0; LED2 = 0; LED3 = 1; case POWERED_STATE: LED1 = 0; LED2 = 1; LED3 = 0; case DEFAULT_STATE: LED1 = 0; LED2 = 1; LED3 = 1; case ADR_PENDING_STATE: LED1 = 1; LED2 = 0; LED3 = 0; case ADDRESS_STATE: LED1 = 1; LED2 = 0; LED3 = 1; case CONFIGURED_STATE: LED1 = 1; LED2 = 1; LED3 = 0; } } while (usb_device_state < CONFIGURED_STATE); while(1); #if 0 // Initiate Osc with 8MHz (only relevant if you use the internal oscillator) //OSCCON = 0x70; initCDC(); // TODO: Remove magic with macro usb_init(cdc_device_descriptor, cdc_config_descriptor, cdc_str_descs, USB_NUM_STRINGS); usb_start(); #if defined (USB_INTERRUPTS) //EnableUsbInterrupt(USB_TRN + USB_SOF + USB_UERR + USB_URST); EnableUsbInterrupt(USB_STALL + USB_IDLE + USB_TRN + USB_ACTIV + USB_SOF + USB_UERR + USB_URST); EnableUsbInterrupts(); #endif usbbufflush(); //flush USB input buffer system led = UCFGbits.UTRDIS; LED0=0; LED1=0; LED2=0; LED3=0; while(1){ LED1 = LED1 ? 0 : 1; for(l = 0; l < 10; ++l); } LED0=1; LED1=1; LED2=1; LED3=1; delay_ms(500); #if 0 while(1) { LED0 = 1; delay_ms(250); LED0 = 0; delay_ms(250); } #endif LED0 = 0; LED1 = 0; LED2 = 0; LED3 = 0; delay_ms(500); while(1); do { LED2=1; LED3 = 0; #ifndef USB_INTERRUPTS //service USB tasks //Guaranteed one pass in polling mode //even when usb_device_state == CONFIGURED_STATE if (!TestUsbInterruptEnabled()) { USBDeviceTasks(); LED3 = 1; } #endif if ((usb_device_state < DEFAULT_STATE)) { // JTR2 no suspendControl available yet || (USBSuspendControl==1) ){ LED0=1; LED1=0; } else if (usb_device_state < CONFIGURED_STATE) { LED0=1; LED1=1; }else if((usb_device_state == CONFIGURED_STATE)) { LED0=0; LED1=1; } LED2=0; delay_ms(1000); } while (usb_device_state < CONFIGURED_STATE); LED0 = 0; LED1 = 0; LED2 = 1; #if 1 while(1) { LED0 = led; led = led ? 0 : 1; #ifndef USB_INTERRUPTS //service USB tasks //Guaranteed one pass in polling mode //even when usb_device_state == CONFIGURED_STATE if (!TestUsbInterruptEnabled()) USBDeviceTasks(); #endif usbbufservice(); //service USB buffer system if (usbbufgetbyte(&c) == 1) { WaitInReady(); cdc_In_buffer[0] = c; //answer OK putUnsignedCharArrayUsbUsart(cdc_In_buffer, 1); } } #endif // Disable USB external transceiver to allow RB1/RB2 UCFGbits.UTRDIS = 0; // set pin to output TRISBbits.TRISB0 = 0; TRISBbits.TRISB1 = 0; TRISBbits.TRISB2 = 0; // start a loop blinking the led while(1) { LED0 = 1; delay_ms(250); LED0 = 0; delay_ms(250); } #endif }
// to go back to the other default, user must unplug USB IR Toy u8 Usb2UartService(void) { static u8 buff_config[5]; switch (Sm_Usb_Uart) { // get configuration data case SM_USB_UART_CONFIG_MODE: { FlushUsbRx(); Usb2Uart_InitUart(TRUE); // TRISC|= 0xC0; // TXSTA= 0x24; // RCSTA= 0x90; // BAUDCON= 0x08; // PIE1= 0x20; //ResetUsbUartTxBuffers(); //ResetUsbUartRxBuffers(); Sm_Usb_Uart=SM_USB_UART_CONFIG_MODE_OK; break; } case SM_USB_UART_CONFIG_MODE_OK: { Sm_Usb_Uart=SM_USB_UART_RUN_MODE; break; } case SM_USB_UART_RUN_MODE: { #if 1 if(getUnsignedCharArrayUsbUart(UsbRxDataBuffer,1)) { TxBuffer[TxBufferCtrIn]=UsbRxDataBuffer[0]; TxBufferCtrIn++; TxBufferCtrIn&=USBUARTBUFCTRMASK; } #endif if(RxBufferCtrIn!=RxBufferCtrOut) //if ((Usb2UartPrepareTxData()==FALSE) && (RxBufferCtrIn!=RxBufferCtrOut)) { if( mUSBUSARTIsTxTrfReady() ) { LAT_LED_PIN^=1; // toggle led every sending irToy.usbOut[0]=RxBuffer[RxBufferCtrOut];//answer OK putUnsignedCharArrayUsbUsart(irToy.usbOut,1); RxBufferCtrOut++; RxBufferCtrOut&=USBUARTBUFCTRMASK; } } break; } } // end of switch // Usb2UartSendTxDataFromBuff(); #if 1 if((TxIf)&&(TxBufferCtrIn!=TxBufferCtrOut)) // If Uart is not full and no data to be sent { TXREG=TxBuffer[TxBufferCtrOut]; TxBufferCtrOut++; TxBufferCtrOut&=USBUARTBUFCTRMASK; } #endif if(RCSTA&0x06) // error handling { RCSTAbits.CREN=0; RCSTAbits.CREN=1; } // this will contain the routine for receiving and transmit return 0;//CONTINUE }
void main(void){ u8 i,cmd, param[9],c; u16 temp; // TODO to be removed later on long l; signed int x, y, z; signed char x8, y8, z8; static unsigned char ledtrig; initCDC(); // JTR this function has been highly modified It no longer sets up CDC endpoints. init(); //setup the crystal, pins mma_init(); usb_init(cdc_device_descriptor, cdc_config_descriptor, cdc_str_descs, USB_NUM_STRINGS); // TODO: Remove magic with macro usb_start(); usbbufflush(); //flush USB input buffer system i = mma_read( MMA_I2CAD ); //if((i&~0b10000000)!=0x1d)while(1); mma_write( MMA_I2CAD, 0x1d | MMA_I2CDIS_bit ); // disable I2C i = mma_read( MMA_CTL1 ); mma_write( MMA_CTL1, i |= MMA_DFBW_bit ); // high output data rate mma_write( MMA_MCTL, 0b00000101 ); // 2g range; measurement mode //mma_calibrate_offset( 0, 0, 0 ); //LEDs //PWM on cathode TRISAbits.TRISA0=0; LATAbits.LATA0=1; //enable cathode //setup LEDs LATB=0; TRISB=0; ledtrig=1; //only shut LED off once // Never ending loop services each task in small increments while (1) { do { if (!TestUsbInterruptEnabled()) //JTR3 added USBDeviceTasks(); ////service USB tasks Guaranteed one pass in polling mode even when usb_device_state == CONFIGURED_STATE if ((usb_device_state < DEFAULT_STATE)) { // JTR2 no suspendControl available yet || (USBSuspendControl==1) ){ //LedOff(); } else if (usb_device_state < CONFIGURED_STATE) { //LedOn(); }else if((ledtrig==1) && (usb_device_state == CONFIGURED_STATE)){ //LedOff(); ledtrig=0; } } while (usb_device_state < CONFIGURED_STATE); usbbufservice();//load any USB data into byte buffer if(usbbufgetbyte(&inByte) == 1){ switch(inByte){//switch on the command case 0x00: WaitInReady(); //it's always ready, but this could be done better param[0]='B'; param[1]='B'; param[2]='I'; param[3]='O'; param[4]='1'; putUnsignedCharArrayUsbUsart(param,5); break; case 0x01: mma_get_average8( 4, &x8, &y8, &z8 ); param[0]=x8; param[1]=y8; param[2]=z8; WaitInReady(); //it's always ready, but this could be done better putUnsignedCharArrayUsbUsart(param,3); break; default: //error break; } }//if data }//while //#endif }//end main