Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00017 #include "nrf24lu1p.h"
00018 #include <stdint.h>
00019 #ifdef __ICC8051__
00020 #include <intrinsics.h>
00021 #endif
00022 #ifdef __C51__
00023 #include <intrins.h>
00024 #endif
00025 
00026 #include "nordic_common.h"
00027 #include "hal_usb_desc.h"
00028 #include "usb.h"
00029 #include "hal_delay.h"
00030 
00031 
00032 #define ALLOCATE_USB_MAP
00033 #include "usb_map.h"
00034 
00035 
00036 
00037 
00038 #define CALCULATE_CS_IN_PTR(ep) (uint8_t xdata*)(&in1cs + 2 * ((ep & 0x7f) - 1 ))
00039 #define CALCULATE_CS_OUT_PTR(ep) (uint8_t xdata*)(&out1cs + 2 * ( (ep & 0x7f) - 1 ))
00040 
00041 
00042 #define CALCULATE_BC_OUT_PTR(ep) (uint8_t xdata *)(&out0bc + (ep * 2 ))
00043 #define CALCULATE_BC_IN_PTR(ep) (uint8_t xdata *)(&in0bc + ((ep & 0x7f ) * 2))
00044 
00045 
00046 #define CALCULATE_BUF_IN_PTR(ep) (uint8_t xdata *)(in0buf - (( ep & 0x7f) * 128))
00047 #define CALCULATE_BUF_OUT_PTR(ep) (uint8_t xdata *)(out0buf - (ep * 128 ))
00048 
00049 static packetizer_t i_packetizer;
00050 static hal_usb_cb_endpoint_t i_endpoint_in_isr[USB_ENDPOINT_IN_COUNT];
00051 static hal_usb_cb_endpoint_t i_endpoint_out_isr[USB_ENDPOINT_OUT_COUNT];
00052 
00053 static hal_usb_device_req req;
00054 hal_usb_t volatile g_hal_usb;
00055 static uint8_t stall_data_size0;
00056 
00057 void hal_usb_init(bool usb_disconnect, hal_usb_cb_device_req_t device_req, hal_usb_cb_reset_t reset, hal_usb_cb_resume_t resume, hal_usb_cb_suspend_t suspend)
00058 {
00059   
00060   g_hal_usb.descs.dev = &g_usb_dev_desc;
00061   g_hal_usb.descs.conf = &g_usb_conf_desc;
00062   g_hal_usb.descs.string = &g_usb_string_desc;
00063 
00064   
00065   g_hal_usb.descs.string_zero[0] = 0x04;
00066   g_hal_usb.descs.string_zero[1] = 0x03;
00067   g_hal_usb.descs.string_zero[2] = 0x09;
00068   g_hal_usb.descs.string_zero[3] = 0x04;
00069 
00070   
00071   g_hal_usb.state = DEFAULT;
00072   g_hal_usb.bm_state = 0;
00073   stall_data_size0 = 0;
00074 
00075   
00076   g_hal_usb.current_config = 0;
00077   g_hal_usb.current_alt_interface = 0;
00078 
00079   
00080   g_hal_usb.device_req = device_req;
00081   g_hal_usb.reset = reset;
00082   g_hal_usb.resume = resume;
00083   g_hal_usb.suspend = suspend;
00084 
00085   
00086   if(usb_disconnect)
00087   {
00088     usbcs |= 0x08; 
00089     delay_ms(50);
00090     usbcs &= ~(0x08); 
00091   }
00092 
00093   
00094   USBWU = 1; 
00095   USB = 1; 
00096 
00097   usbien = 0x1d; 
00098 
00099   in_ien = 0x01;
00100   in_irq = 0x1f;
00101   out_ien = 0x01;
00102   out_irq = 0x1f;
00103 
00104   
00105   bout1addr = 16;
00106   bout2addr = 32;
00107   bout3addr = 48;
00108   bout4addr = 64;
00109   bout5addr = 80;
00110 
00111   binstaddr = 0xc0;
00112   bin1addr = 16;
00113   bin2addr = 32;
00114   bin3addr = 48;
00115   bin4addr = 64;
00116   bin5addr = 80;
00117 
00118   
00119   inbulkval = 0x01;
00120   outbulkval = 0x01;
00121   inisoval = 0x00;
00122   outisoval = 0x00;
00123 }
00124 
00125 void hal_usb_endpoint_stall(uint8_t ep_num, bool stall)
00126 {
00127   uint8_t temp;
00128   uint8_t xdata *cs_ptr;
00129 
00130   temp = 2 * ((ep_num & 0x7f) - 1);
00131 
00132   
00133   if((ep_num & 0x80 ) == 0x80) 
00134   {
00135     
00136     cs_ptr = (uint8_t xdata*)(&in1cs + temp);
00137   }
00138   else 
00139   {
00140     
00141     cs_ptr = (uint8_t xdata*)(&out1cs + temp);
00142   }
00143 
00144   if(stall == true)
00145   {
00146     
00147     *cs_ptr = 0x01;
00148   }
00149   else
00150   {
00151     
00152     *cs_ptr = 0x00;
00153   }
00154 }
00155 
00156 uint8_t hal_usb_get_address()
00157 {
00158   return fnaddr;
00159 }
00160 
00161 void hal_usb_endpoint_config(uint8_t ep_num, uint8_t ep_size, hal_usb_cb_endpoint_t endpoint_isr)
00162 {
00163   uint8_t xdata *bc_ptr;
00164   uint8_t temp = (ep_num & 0x7f) - 1;
00165   uint8_t stemp = 1 << (ep_num & 0x7f);
00166 
00167   
00168   ep_size = 0;
00169 
00170   if((ep_num & 0x80 ) == 0x80) 
00171   {
00172     i_endpoint_in_isr[temp] = endpoint_isr;
00173     if(endpoint_isr != NULL)
00174     {
00175       
00176       in_ien |= stemp; 
00177       inbulkval |= stemp;
00178     }
00179     else
00180     {
00181       
00182       in_ien &= ~stemp;
00183       inbulkval &= ~stemp;
00184     }
00185   }
00186   else 
00187   {
00188     i_endpoint_out_isr[temp] = endpoint_isr;
00189     if(endpoint_isr != NULL)
00190     {
00191       
00192       out_ien |= stemp;
00193       outbulkval |= stemp;
00194 
00195       
00196       bc_ptr = CALCULATE_BC_OUT_PTR(ep_num);
00197       *bc_ptr = 0xff;
00198     }
00199     else
00200     {
00201       
00202       out_ien &= ~stemp;
00203       outbulkval &= ~stemp;
00204     }
00205   }
00206 }
00207 
00208 void hal_usb_wakeup()
00209 {
00210   
00211   if((g_hal_usb.bm_state & USB_BM_STATE_ALLOW_REMOTE_WAKEUP) == USB_BM_STATE_ALLOW_REMOTE_WAKEUP)
00212   {
00213     USBCON = 0x40;  
00214     delay_ms(1);    
00215     USBCON = 0x00;
00216   }
00217 }
00218 
00219 void hal_usb_reset()
00220 {
00221   SWRST = 1;  
00222 }
00223 
00224 #pragma disable
00225 hal_usb_state_t hal_usb_get_state()
00226 {
00227   return g_hal_usb.state;
00228 }
00229 
00230 void hal_usb_send_data(uint8_t ep_num, uint8_t* array, uint8_t count)
00231 {
00232   uint8_t i;
00233 
00234   uint8_t xdata *buf_ptr;
00235   uint8_t xdata *bc_ptr;
00236 
00237   
00238   buf_ptr = CALCULATE_BUF_IN_PTR(ep_num);
00239   bc_ptr = CALCULATE_BC_IN_PTR(ep_num);
00240 
00241   
00242   for( i = 0; i < count; i++ )
00243   {
00244     buf_ptr[i] = array[i];
00245   }
00246 
00247   
00248   *bc_ptr = count;
00249 }
00250 
00251 void hal_usb_bus_disconnect()
00252 {
00253   usbcs |= 0x08; 
00254 }
00255 
00256 void hal_usb_bus_connect()
00257 {
00258   usbcs &= ~(0x08); 
00259 }
00260 
00261 void hal_usb_sleep()
00262 {
00263   USBSLP = 1;
00264 }
00265  
00266 static void packetize(uint8_t *data_ptr, uint8_t data_size)
00267 {
00268   i_packetizer.data_ptr = data_ptr;
00269   i_packetizer.data_size = data_size;
00270   i_packetizer.pkt_size = g_hal_usb.descs.dev->bMaxPacketSize0;
00271 }
00272 
00273 
00274 static void packetizer_isr_ep0_in(void) 
00275 {
00276   uint8_t size, i;
00277 
00278   
00279   if(i_packetizer.data_size == 0)
00280   {        
00281     if (stall_data_size0 == 1)
00282     {
00283         USB_EP0_DSTALL();
00284     }
00285     else
00286     {
00287         stall_data_size0 = 1;
00288         in0bc = 0;
00289         USB_EP0_HSNAK();
00290     }       
00291     return;
00292   }
00293 
00294   size = MIN(i_packetizer.data_size, i_packetizer.pkt_size);
00295 
00296   
00297   for(i = 0; i < size; i++)
00298   {
00299     in0buf[i] = i_packetizer.data_ptr[i];
00300   }
00301 
00302   if (size < i_packetizer.pkt_size)
00303     stall_data_size0 = 1;
00304   
00305   
00306   in0bc = size;
00307 
00308   
00309   i_packetizer.data_ptr += size;
00310   i_packetizer.data_size -= size;
00311 
00312   return;
00313 }
00314 
00316 static void usb_process_dev_req_cb_response(void)
00317 {
00318   uint8_t *data_ptr;
00319   uint8_t data_size;
00320   hal_usb_dev_req_resp_t ret = g_hal_usb.device_req(&req, &data_ptr, &data_size);
00321 
00322   switch(ret)
00323   {
00324     case DATA:
00325       packetize((uint8_t *)data_ptr, MIN(req.wLength, data_size));
00326       packetizer_isr_ep0_in();
00327       break;
00328     case NO_RESPONSE:
00329       break;
00330     case EMPTY_RESPONSE:
00331     case NAK:
00332       USB_EP0_HSNAK();
00333       break;
00334     case ACK:
00335       out0bc = 0xff;
00336       break;
00337     case STALL:
00338     default:
00339       USB_EP0_STALL();
00340       break;
00341     }
00342 }
00343 
00344 static void usb_process_get_status(void)
00345 {
00346   uint8_t xdata *ptr;
00347 
00348   if(g_hal_usb.state == ADDRESSED)
00349   {
00350     if(req.wIndex != 0x00)
00351     {
00352         USB_EP0_STALL();
00353     }
00354     else
00355     {
00356       in0buf[0] = in0buf[1] = 
00357         ((g_hal_usb.descs.conf->conf.bmAttributes & 0x40 ) >> 6); 
00358       in0bc = 0x02;
00359     }
00360   }
00361   else if(g_hal_usb.state == CONFIGURED)
00362   {
00363     in0buf[1] = 0x00;
00364     switch(req.bmRequestType)
00365     {
00366       case 0x80: 
00367         if((g_hal_usb.bm_state & USB_BM_STATE_ALLOW_REMOTE_WAKEUP ) == USB_BM_STATE_ALLOW_REMOTE_WAKEUP)
00368         {
00369             in0buf[0] = 0x02;
00370         }
00371         else
00372         {
00373             in0buf[0] = 0x00;
00374         }
00375 
00376         in0buf[0] |= ((g_hal_usb.descs.conf->conf.bmAttributes & 0x40 ) >> 6); 
00377         in0bc = 0x02;
00378         break;
00379       case 0x81: 
00380         in0buf[0] = 0x00;
00381         in0bc = 0x02;
00382         break;
00383       case 0x82: 
00384         if((req.wIndex & 0x80) == 0x80) 
00385         {
00386           ptr = CALCULATE_CS_IN_PTR(req.wIndex);
00387         }
00388         else
00389         {
00390           ptr = CALCULATE_CS_OUT_PTR(req.wIndex);
00391         }
00392 
00393         in0buf[0] = *ptr & 0x01;
00394         in0bc = 0x02;
00395         break;
00396       default:
00397         USB_EP0_STALL();
00398         break;
00399     } 
00400   }
00401   else
00402   {
00403     
00404     USB_EP0_STALL();
00405   }
00406 }
00407 
00408 static void usb_process_get_descriptor(void)
00409 {
00410   
00411   switch(req.wValueMsb)
00412   {
00413     case USB_DESC_DEVICE:
00414       packetize((uint8_t *)g_hal_usb.descs.dev,
00415       MIN(req.wLength, sizeof(hal_usb_dev_desc_t)));
00416       packetizer_isr_ep0_in();
00417       break;
00418     case USB_DESC_CONFIGURATION:
00419       
00420       packetize((uint8_t *)g_hal_usb.descs.conf,
00421       MIN(req.wLength, sizeof(usb_conf_desc_templ_t)));
00422       packetizer_isr_ep0_in();
00423       break;
00424     case USB_DESC_STRING:
00425       
00426       if(req.wValueLsb == 0x00)
00427       {
00428         packetize(g_hal_usb.descs.string_zero, MIN(req.wLength, sizeof(g_hal_usb.descs.string_zero)));
00429         packetizer_isr_ep0_in();
00430       }
00431       else
00432       {
00433         if((req.wValueLsb - 1 ) < USB_STRING_DESC_COUNT)
00434         {
00435           packetize((uint8_t *)(g_hal_usb.descs.string->idx[req.wValueLsb-1]),
00436           MIN(req.wLength, g_hal_usb.descs.string->idx[req.wValueLsb-1][0]));
00437           packetizer_isr_ep0_in();
00438         }
00439         else
00440         {
00441           USB_EP0_STALL();
00442         }
00443       }
00444       break;
00445     case USB_DESC_INTERFACE:
00446     case USB_DESC_ENDPOINT:
00447     case USB_DESC_DEVICE_QUAL:
00448     case USB_DESC_OTHER_SPEED_CONF:
00449     case USB_DESC_INTERFACE_POWER:
00450       USB_EP0_STALL();
00451       break;
00452     default:
00453       usb_process_dev_req_cb_response();
00454       break;
00455   }
00456 }
00457 
00458 static void isr_sudav(void)
00459 {
00460   
00461   req.bmRequestType = setupbuf[0];
00462   req.bRequest = setupbuf[1];
00463   req.wValueLsb = setupbuf[2];
00464   req.wValueMsb = setupbuf[3];
00465   req.wIndex = setupbuf[4];
00466   req.wLength = setupbuf[6];
00467   if (setupbuf[7] > 0)
00468   {
00469     req.wLength = 0xff; 
00470   }
00471 
00472   
00473   if((req.bmRequestType & 0x60) == 0x00)
00474   {
00475     switch(req.bRequest)
00476     {
00477       case USB_REQ_GET_DESCRIPTOR:
00478         usb_process_get_descriptor();
00479         break;
00480       case USB_REQ_GET_STATUS:
00481         usb_process_get_status();
00482         break;           
00483       case USB_REQ_CLEAR_FEATURE:
00484       case USB_REQ_SET_FEATURE: 
00485         switch(req.bmRequestType)
00486         {
00487           case 0x00: 
00488             if(req.wValueLsb == USB_DEVICE_REMOTE_WAKEUP)
00489             {
00490               if (req.bRequest == USB_REQ_CLEAR_FEATURE) 
00491                 g_hal_usb.bm_state &= ~(USB_BM_STATE_ALLOW_REMOTE_WAKEUP);
00492               else
00493                 g_hal_usb.bm_state |= USB_BM_STATE_ALLOW_REMOTE_WAKEUP;
00494               USB_EP0_HSNAK();
00495             }
00496             else
00497             {
00498               USB_EP0_STALL();
00499             }
00500             break;
00501 
00502           case 0x02: 
00503             if(req.wValueLsb == USB_ENDPOINT_HALT)
00504             {
00505               if (req.bRequest == USB_REQ_CLEAR_FEATURE) 
00506                 hal_usb_endpoint_stall(req.wIndex, false);
00507               else
00508                 hal_usb_endpoint_stall(req.wIndex, true);
00509               USB_EP0_HSNAK();
00510             }
00511             else 
00512             {
00513                 USB_EP0_STALL();
00514             }
00515             break;
00516           case 0x01: 
00517           default:
00518             USB_EP0_STALL();
00519             break;
00520         }
00521         break;
00522 
00523       case USB_REQ_SET_ADDRESS:
00524         g_hal_usb.state = ADDRESSED;
00525         g_hal_usb.current_config = 0x00;
00526         break;
00527       case USB_REQ_GET_CONFIGURATION:
00528         switch(g_hal_usb.state)
00529         {
00530           case ADDRESSED:
00531             in0buf[0] = 0x00;
00532             in0bc = 0x01;
00533             break;
00534           case CONFIGURED:
00535             in0buf[0] = g_hal_usb.current_config;
00536             in0bc = 0x01;
00537             break;
00538           default:
00539             USB_EP0_STALL();
00540             break;
00541         }
00542         break;
00543       case USB_REQ_SET_CONFIGURATION:
00544         switch(req.wValueLsb)
00545         {
00546           case 0x00:
00547             g_hal_usb.state = ADDRESSED;
00548             g_hal_usb.current_config = 0x00;
00549             USB_EP0_HSNAK();
00550             break;
00551           case 0x01:
00552             g_hal_usb.state = CONFIGURED;
00553             g_hal_usb.bm_state |= USB_BM_STATE_CONFIGURED;
00554             g_hal_usb.current_config = 0x01;
00555             USB_EP0_HSNAK();
00556             break;
00557           default:
00558             USB_EP0_STALL();
00559             break;
00560         }
00561         break;
00562       case USB_REQ_GET_INTERFACE: 
00563         in0buf[0] = g_hal_usb.current_alt_interface;
00564         in0bc = 0x01;
00565         break;
00566       case USB_REQ_SET_DESCRIPTOR:
00567       case USB_REQ_SET_INTERFACE: 
00568       case USB_REQ_SYNCH_FRAME:   
00569       default:
00570        USB_EP0_STALL();
00571        break;
00572     };
00573   } 
00574   
00575   else if((req.bmRequestType & 0x60 ) == 0x20)  
00576   {
00577     if(req.wLength != 0 && ((req.bmRequestType & 0x80) == 0x00))
00578     {
00579       
00580       
00581       out0bc = 0xff;
00582     }
00583     else
00584     {
00585       usb_process_dev_req_cb_response();
00586     }
00587     
00588   } 
00589   else  
00590   {
00591     USB_EP0_STALL();
00592   }
00593 }
00594 
00595 static void isr_suspend(void)
00596 {
00597   uint8_t allow_remote_wu = 0;
00598   g_hal_usb.bm_state &= ~(USB_BM_STATE_HOST_WU); 
00599 
00600   if( g_hal_usb.state == CONFIGURED )
00601   {
00602     if( ( g_hal_usb.bm_state & USB_BM_STATE_ALLOW_REMOTE_WAKEUP ) == USB_BM_STATE_ALLOW_REMOTE_WAKEUP )
00603     {
00604       allow_remote_wu = 1;
00605     }
00606   }
00607 
00608   g_hal_usb.state = SUSPENDED;
00609 
00610   if( g_hal_usb.suspend != NULL )
00611   {
00612     g_hal_usb.suspend(allow_remote_wu);
00613   }
00614 }
00615 
00616 static void isr_usbreset(void)
00617 {
00618   g_hal_usb.state = DEFAULT;
00619   g_hal_usb.current_config = 0;
00620   g_hal_usb.current_alt_interface = 0;
00621   g_hal_usb.bm_state = 0;
00622   if( g_hal_usb.reset != NULL ) g_hal_usb.reset();
00623 }
00624 
00625 
00626 USB_WU_ISR() 
00627 {
00628 #define ICH4
00629   #ifdef ICH4
00630   uint8_t t;
00631   #endif
00632 
00633   
00634   
00635   
00636   if( ( usbcs & 0x80 ) == 0x80 )
00637   {
00638     
00639     usbcs = 0x80;
00640 
00641     
00642     if( ( g_hal_usb.bm_state & USB_BM_STATE_ALLOW_REMOTE_WAKEUP ) == USB_BM_STATE_ALLOW_REMOTE_WAKEUP )
00643     {
00644   #ifdef ICH4
00645       
00646       usbcs |= 0x02;
00647 
00648       
00649       _nop_();
00650       _nop_();
00651 
00652       t = usbcs;
00653 
00654       
00655       t &= ~0x02;
00656 
00657       
00658       t |= 0x01;
00659 
00660       
00661       
00662       usbcs = t;
00663 #else
00664       usbcs |= 0x01;  
00665 #endif
00666       delay_ms(7); 
00667                     
00668 
00669       usbcs &= ~0x01; 
00670     }
00671   }
00672   else 
00673   {
00674     
00675     g_hal_usb.bm_state |= USB_BM_STATE_HOST_WU;
00676   }
00677 
00678   if((g_hal_usb.bm_state & USB_BM_STATE_CONFIGURED ) == USB_BM_STATE_CONFIGURED)
00679   {
00680     g_hal_usb.state = CONFIGURED;
00681   }
00682   else
00683   {
00684     g_hal_usb.state = DEFAULT;
00685   }
00686 
00687   
00688   g_hal_usb.resume();
00689 }
00690 
00691 
00692 static void usb_process_ep_response(uint8_t ret, uint8_t xdata* cs_ptr, uint8_t xdata* bc_ptr)
00693 {
00694   if( ret == 0xff ) 
00695   {
00696     *bc_ptr = 0xff;
00697   }
00698   else if( ( ret & 0x80 ) == 0x80 )  
00699   {
00700     *cs_ptr = 0x01;
00701   }
00702   else if( ( ret & 0x60 ) == 0x60 ) 
00703   {
00704     *cs_ptr = 0x02;
00705   }
00706   else if( ret == 0 ) 
00707   {
00708     *bc_ptr = 0;
00709   }
00710   else
00711   {
00712     *bc_ptr = ret;
00713   }
00714 }
00715 
00716 USB_ISR()
00717 {
00718   uint8_t ep;
00719   uint8_t ret;
00720   uint8_t xdata *cs_ptr;
00721   uint8_t xdata *buf_ptr;
00722   uint8_t xdata *bc_ptr;
00723 
00724   switch(ivec)
00725   {
00726     case INT_SUDAV:
00727       usbirq = 0x01;
00728       isr_sudav();
00729       break;
00730     case INT_SOF:
00731       usbirq = 0x02;
00732       break;
00733     case INT_SUTOK:
00734       usbirq = 0x04;
00735       i_packetizer.data_ptr = NULL;
00736       i_packetizer.data_size = 0;
00737       i_packetizer.pkt_size = 0;
00738       stall_data_size0 = 0;
00739       break;
00740     case INT_SUSPEND:
00741       usbirq = 0x08;
00742       isr_suspend();
00743       break;
00744     case INT_USBRESET:
00745       usbirq = 0x10;
00746       isr_usbreset();
00747       break;
00748     case INT_EP0IN:
00749       in_irq = 0x01;
00750       packetizer_isr_ep0_in();
00751       break;
00752     case INT_EP0OUT:
00753       out_irq = 0x01;
00754       i_packetizer.data_size = 0;
00755       usb_process_dev_req_cb_response();
00756       break;
00757       case INT_EP1IN:
00758       case INT_EP2IN:
00759       case INT_EP3IN:
00760       case INT_EP4IN:
00761       case INT_EP5IN:
00762         
00763         ep = (ivec - INT_EP0IN ) >> 3;
00764         
00765         in_irq = ( 1 << ep );
00766 
00767         cs_ptr = CALCULATE_CS_IN_PTR(ep);
00768         buf_ptr = CALCULATE_BUF_IN_PTR(ep);
00769         bc_ptr = CALCULATE_BC_IN_PTR(ep);
00770     
00771         
00772         ret = i_endpoint_in_isr[ep - 1](buf_ptr, bc_ptr);
00773         usb_process_ep_response(ret, cs_ptr, bc_ptr);
00774         break;
00775       case INT_EP1OUT:
00776       case INT_EP2OUT:
00777       case INT_EP3OUT:
00778       case INT_EP4OUT:
00779       case INT_EP5OUT:
00780         
00781         ep = (ivec - INT_EP0OUT) >> 3;          
00782 
00783         
00784         out_irq = ( 1 << ep );
00785         
00786         cs_ptr = CALCULATE_CS_OUT_PTR(ep);
00787         buf_ptr = CALCULATE_BUF_OUT_PTR(ep);
00788         bc_ptr = CALCULATE_BC_OUT_PTR(ep);
00789 
00790         
00791         ret = (i_endpoint_out_isr[ep - 1])(buf_ptr, bc_ptr);
00792         usb_process_ep_response(ret, cs_ptr, bc_ptr);
00793         break;
00794     default:
00795       break;
00796   };
00797 }