Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 
00034 
00035 
00036 
00037 
00038 
00039 
00040 
00041 
00042 
00043 
00044 
00045 
00046 
00047 
00048 
00049 
00050 
00051 
00052 
00053 
00054 
00055 
00056 
00057 
00058 
00059 
00060 
00061 
00062 
00063 
00064 
00065 
00066 
00067 
00068 
00069 
00070 
00071 
00072 
00073 
00074 
00075 
00076 
00077 #include <cfg/arch/avr.h>
00078 
00079 
00080 
00081 
00082 
00083 #include <dev/spidigio.h>
00084 
00085 
00086 
00087 
00088 #ifndef SPIDIGIO_SOUT_BIT
00089 #define SPIDIGIO_SOUT_BIT 5
00090 #define SPIDIGIO_SOUT_AVRPORT AVRPORTD
00091 #define SPIDIGIO_SIN_BIT 6
00092 #define SPIDIGIO_SIN_AVRPORT AVRPORTD
00093 #define SPIDIGIO_SCLK_BIT 7
00094 #define SPIDIGIO_SCLK_AVRPORT AVRPORTD
00095 #define SPIDIGIO_LDI_BIT 7
00096 #define SPIDIGIO_LDI_AVRPORT AVRPORTB
00097 #define SPIDIGIO_LDO_BIT 5
00098 #define SPIDIGIO_LDO_AVRPORT AVRPORTB
00099 #endif
00100 
00101 #if (SPIDIGIO_SOUT_AVRPORT == AVRPORTB)
00102 #define SPIDIGIO_SOUT_PORT  PORTB
00103 #define SPIDIGIO_SOUT_DDR   DDRB
00104 
00105 #elif (SPIDIGIO_SOUT_AVRPORT == AVRPORTD)
00106 #define SPIDIGIO_SOUT_PORT  PORTD
00107 #define SPIDIGIO_SOUT_DDR   DDRD
00108 
00109 #elif (SPIDIGIO_SOUT_AVRPORT == AVRPORTE)
00110 #define SPIDIGIO_SOUT_PORT  PORTE
00111 #define SPIDIGIO_SOUT_DDR   DDRE
00112 
00113 #elif (SPIDIGIO_SOUT_AVRPORT == AVRPORTF)
00114 #define SPIDIGIO_SOUT_PORT  PORTF
00115 #define SPIDIGIO_SOUT_DDR   DDRF
00116 
00117 #endif
00118 
00119 #if (SPIDIGIO_SIN_AVRPORT == AVRPORTB)
00120 #define SPIDIGIO_SIN_PORT   PORTB
00121 #define SPIDIGIO_SIN_PIN    PINB
00122 #define SPIDIGIO_SIN_DDR    DDRB
00123 
00124 #elif (SPIDIGIO_SIN_AVRPORT == AVRPORTD)
00125 #define SPIDIGIO_SIN_PORT   PORTD
00126 #define SPIDIGIO_SIN_PIN    PIND
00127 #define SPIDIGIO_SIN_DDR    DDRD
00128 
00129 #elif (SPIDIGIO_SIN_AVRPORT == AVRPORTE)
00130 #define SPIDIGIO_SIN_PORT   PORTE
00131 #define SPIDIGIO_SIN_PIN    PINE
00132 #define SPIDIGIO_SIN_DDR    DDRE
00133 
00134 #elif (SPIDIGIO_SIN_AVRPORT == AVRPORTF)
00135 #define SPIDIGIO_SIN_PORT   PORTF
00136 #define SPIDIGIO_SIN_PIN    PINF
00137 #define SPIDIGIO_SIN_DDR    DDRF
00138 #endif
00139 
00140 #if (SPIDIGIO_SCLK_AVRPORT == AVRPORTB)
00141 #define SPIDIGIO_SCLK_PORT  PORTB
00142 #define SPIDIGIO_SCLK_DDR   DDRB
00143 
00144 #elif (SPIDIGIO_SCLK_AVRPORT == AVRPORTD)
00145 #define SPIDIGIO_SCLK_PORT  PORTD
00146 #define SPIDIGIO_SCLK_DDR   DDRD
00147 
00148 #elif (SPIDIGIO_SCLK_AVRPORT == AVRPORTE)
00149 #define SPIDIGIO_SCLK_PORT  PORTE
00150 #define SPIDIGIO_SCLK_DDR   DDRE
00151 
00152 #elif (SPIDIGIO_SCLK_AVRPORT == AVRPORTF)
00153 #define SPIDIGIO_SCLK_PORT  PORTF
00154 #define SPIDIGIO_SCLK_DDR   DDRF
00155 
00156 #endif 
00157 
00158 #if (SPIDIGIO_LDO_AVRPORT == AVRPORTB)
00159 #define SPIDIGIO_LDO_PORT   PORTB
00160 #define SPIDIGIO_LDO_DDR    DDRB
00161 
00162 #elif (SPIDIGIO_LDO_AVRPORT == AVRPORTD)
00163 #define SPIDIGIO_LDO_PORT   PORTD
00164 #define SPIDIGIO_LDO_DDR    DDRD
00165 
00166 #elif (SPIDIGIO_LDO_AVRPORT == AVRPORTE)
00167 #define SPIDIGIO_LDO_PORT   PORTE
00168 #define SPIDIGIO_LDO_DDR    DDRE
00169 
00170 #elif (SPIDIGIO_LDO_AVRPORT == AVRPORTF)
00171 #define SPIDIGIO_LDO_PORT   PORTF
00172 #define SPIDIGIO_LDO_DDR    DDRF
00173 
00174 #endif 
00175 
00176 #if (SPIDIGIO_LDI_AVRPORT == AVRPORTB)
00177 #define SPIDIGIO_LDI_PORT   PORTB
00178 #define SPIDIGIO_LDI_DDR    DDRB
00179 
00180 #elif (SPIDIGIO_LDI_AVRPORT == AVRPORTD)
00181 #define SPIDIGIO_LDI_PORT   PORTD
00182 #define SPIDIGIO_LDI_DDR    DDRD
00183 
00184 #elif (SPIDIGIO_LDI_AVRPORT == AVRPORTE)
00185 #define SPIDIGIO_LDI_PORT   PORTE
00186 #define SPIDIGIO_LDI_DDR    DDRE
00187 
00188 #elif (SPIDIGIO_LDI_AVRPORT == AVRPORTF)
00189 #define SPIDIGIO_LDI_PORT   PORTF
00190 #define SPIDIGIO_LDI_DDR    DDRF
00191 
00192 #endif 
00193 
00198 
00199 static ureg_t us_loops = 1;
00200 
00216 static INLINE void delay_us(ureg_t us)
00217 {
00218     ureg_t _cnt = us * us_loops;
00219 
00220     while (_cnt--) {
00221         
00222 
00223 
00224 
00225 
00226         _NOP();
00227     }
00228 }
00229 
00241 static INLINE void ShiftDigital(void)
00242 {
00243     
00244     cbi(SPIDIGIO_SCLK_PORT, SPIDIGIO_SCLK_BIT);
00245     
00246     delay_us(4);
00247 
00248     
00249     sbi(SPIDIGIO_SCLK_PORT, SPIDIGIO_SCLK_BIT);
00250     
00251     delay_us(4);
00252 }
00253 
00272 uint32_t SpiDigitalGet(ureg_t num)
00273 {
00274     uint32_t bits = 0;
00275 
00276     cbi(SPIDIGIO_SOUT_PORT, SPIDIGIO_SOUT_BIT);
00277 
00278     
00279 
00280 
00281 
00282 
00283     sbi(SPIDIGIO_LDI_PORT, SPIDIGIO_LDI_BIT);
00284     delay_us(4);
00285     cbi(SPIDIGIO_LDI_PORT, SPIDIGIO_LDI_BIT);
00286     delay_us(4);
00287 
00288     
00289     while (num--) {
00290         
00291         bits <<= 1;
00292 
00293         
00294 
00295 
00296 
00297 
00298 
00299         if (bit_is_set(SPIDIGIO_SIN_PIN, SPIDIGIO_SIN_BIT)) {
00300             bits |= 1;
00301         }
00302 
00303         
00304 
00305 
00306 
00307         ShiftDigital();
00308     }
00309     return bits;
00310 }
00311 
00326 void SpiDigitalSet(ureg_t num, uint32_t bits)
00327 {
00328     uint32_t mask;
00329 
00330     
00331     if (num) {
00332         
00333 
00334 
00335 
00336 
00337 
00338 
00339         mask = 1UL << (num - 1);
00340 
00341         
00342         while (num--) {
00343 
00344             
00345 
00346 
00347 
00348 
00349 
00350             if (bits & mask) {
00351                 
00352                 sbi(SPIDIGIO_SOUT_PORT, SPIDIGIO_SOUT_BIT);
00353             } 
00354             else {
00355                 
00356                 cbi(SPIDIGIO_SOUT_PORT, SPIDIGIO_SOUT_BIT);
00357             }
00358 
00359             
00360             delay_us(4);
00361 
00362             
00363             ShiftDigital();
00364 
00365             
00366             mask >>= 1;
00367         }
00368 
00369         
00370 
00371 
00372 
00373         cbi(SPIDIGIO_LDO_PORT, SPIDIGIO_LDO_BIT);
00374         delay_us(4);
00375         sbi(SPIDIGIO_LDO_PORT, SPIDIGIO_LDO_BIT);
00376     }
00377 }
00378 
00404 static ureg_t CountDigitalShifts(ureg_t num, ureg_t bit, ureg_t smode)
00405 {
00406     ureg_t i;
00407     ureg_t rc = 0;
00408 
00409     
00410 
00411 
00412 
00413     if (smode) {
00414         sbi(SPIDIGIO_LDI_PORT, SPIDIGIO_LDI_BIT);
00415         delay_us(4);
00416         cbi(SPIDIGIO_LDI_PORT, SPIDIGIO_LDI_BIT);
00417     }
00418 
00419     
00420 
00421 
00422     if (bit) {
00423         sbi(SPIDIGIO_SOUT_PORT, SPIDIGIO_SOUT_BIT);
00424     } else {
00425         cbi(SPIDIGIO_SOUT_PORT, SPIDIGIO_SOUT_BIT);
00426     }
00427     delay_us(4);
00428 
00429     
00430 
00431 
00432 
00433     for (i = 0; i < num; i++) {
00434         if (bit_is_set(SPIDIGIO_SIN_PIN, SPIDIGIO_SIN_BIT)) {
00435             if (bit) {
00436                 if (smode) {
00437                     rc = i + 1;
00438                 } else if (rc == 0) {
00439                     rc = i + 1;
00440                 }
00441             }
00442         } else {
00443             if (bit == 0) {
00444                 if (smode) {
00445                     rc = i + 1;
00446                 } else if (rc == 0) {
00447                     rc = i + 1;
00448                 }
00449             }
00450         }
00451         ShiftDigital();
00452     }
00453     return rc;
00454 }
00455 
00471 void SpiDigitalInit(ureg_t * inputs, ureg_t * outputs)
00472 {
00473     ureg_t total = 0;
00474     ureg_t i;
00475     ureg_t cnt;
00476 
00477     
00478 
00479 
00480     if ((us_loops = (NutGetCpuClock() + 500000UL) / 4000000UL) < 1) {
00481         us_loops = 1;
00482     }
00483 
00484     
00485 
00486 
00487     sbi(SPIDIGIO_SOUT_DDR, SPIDIGIO_SOUT_BIT);
00488 
00489     
00490 
00491 
00492     sbi(SPIDIGIO_SIN_PORT, SPIDIGIO_SIN_BIT);
00493     cbi(SPIDIGIO_SIN_DDR, SPIDIGIO_SIN_BIT);
00494 
00495     
00496 
00497 
00498 
00499     sbi(SPIDIGIO_SCLK_PORT, SPIDIGIO_SCLK_BIT);
00500     sbi(SPIDIGIO_SCLK_DDR, SPIDIGIO_SCLK_BIT);
00501 
00502     
00503 
00504 
00505 
00506     sbi(SPIDIGIO_LDO_PORT, SPIDIGIO_LDO_BIT);
00507     sbi(SPIDIGIO_LDO_DDR, SPIDIGIO_LDO_BIT);
00508 
00509     
00510 
00511 
00512 
00513     cbi(SPIDIGIO_LDI_PORT, SPIDIGIO_LDI_BIT);
00514     sbi(SPIDIGIO_LDI_DDR, SPIDIGIO_LDI_BIT);
00515 
00516     
00517 
00518 
00519 
00520 
00521     CountDigitalShifts(32, 0, 0);
00522     total = CountDigitalShifts(32, 1, 0) - 1;
00523 
00524     
00525 
00526 
00527 
00528 
00529     *inputs = 0;
00530     for (i = 0; i < 5; i++) {
00531         if ((cnt = CountDigitalShifts(total, 0, 1)) > *inputs) {
00532             *inputs = cnt;
00533         }
00534         if ((cnt = CountDigitalShifts(total, 1, 1)) > *inputs) {
00535             *inputs = cnt;
00536         }
00537     }
00538     *outputs = total - *inputs;
00539 }
00540 
00541