Changeset 204 for soft/giet_vm/sys/drivers.c
- Timestamp:
- Aug 14, 2012, 8:14:55 PM (12 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
soft/giet_vm/sys/drivers.c
r203 r204 17 17 // 18 18 // The following global parameters must be defined in the giet_config.h file: 19 // - CLUSTER_IO_ID 20 // - CLUSTER_SIZE 19 21 // - NB_CLUSTERS 20 22 // - NB_PROCS_MAX … … 23 25 // - NB_TTYS 24 26 // 25 // The following virtual base addresses must be defined in the sys.ld file:27 // The following virtual base addresses must be defined in the giet.ld file: 26 28 // - seg_icu_base 27 29 // - seg_tim_base … … 31 33 // - seg_fbf_base 32 34 // - seg_ioc_base 35 // As some peripherals can be replicated in the clusters (ICU, TIMER, DMA) 36 // These addresses must be completed by an offset depending on the cluster index 37 // full_base_address = seg_***_base + cluster_id * CLUSTER_SIZE 33 38 /////////////////////////////////////////////////////////////////////////////////// 34 39 … … 54 59 #endif 55 60 56 #if !defined(CLUSTER_S PAN)57 # error: You must define CLUSTER_S PANin 'giet_config.h' file61 #if !defined(CLUSTER_SIZE) 62 # error: You must define CLUSTER_SIZE in 'giet_config.h' file 58 63 #endif 59 64 … … 132 137 133 138 #if GIET_USE_XICU 134 unsigned int* timer_address = (unsigned int*) &seg_icu_base +135 (cluster_id * CLUSTER_S PAN);139 unsigned int* timer_address = (unsigned int*)((char*)&seg_icu_base + 140 (cluster_id * CLUSTER_SIZE) ); 136 141 137 142 timer_address[XICU_REG(XICU_PTI_PER, local_id)] = period; 138 143 #else 139 unsigned int* timer_address = (unsigned int*) &seg_tim_base +140 (cluster_id * CLUSTER_S PAN);144 unsigned int* timer_address = (unsigned int*)((char*)&seg_tim_base + 145 (cluster_id * CLUSTER_SIZE) ); 141 146 142 147 timer_address[local_id * TIMER_SPAN + TIMER_PERIOD] = period; … … 160 165 161 166 #if GIET_USE_XICU 162 unsigned int* timer_address = (unsigned int*) &seg_icu_base +163 (cluster_id * CLUSTER_S PAN);167 unsigned int* timer_address = (unsigned int*)((char*)&seg_icu_base + 168 (cluster_id * CLUSTER_SIZE) ); 164 169 165 170 timer_address[XICU_REG(XICU_PTI_PER, local_id)] = 0; 166 171 #else 167 unsigned int* timer_address = (unsigned int*) &seg_tim_base +168 (cluster_id * CLUSTER_S PAN);172 unsigned int* timer_address = (unsigned int*)((char*)&seg_tim_base + 173 (cluster_id * CLUSTER_SIZE) ); 169 174 170 175 timer_address[local_id * TIMER_SPAN + TIMER_MODE] = 0; … … 176 181 // _timer_reset_irq() 177 182 // This function acknowlegge a timer interrupt in the vci_timer (or vci_xicu) 178 // component by writing in the proper register the period value.183 // component by reading/writing in the proper register. 179 184 // It can be used by both the isr_switch() for a "system" timer, 180 185 // or by the _isr_timer() for an "user" timer. … … 189 194 190 195 #if GIET_USE_XICU 191 unsigned int* timer_address = (unsigned int*) &seg_icu_base +192 (cluster_id * CLUSTER_SPAN);196 unsigned int* timer_address = (unsigned int*)((char*)&seg_icu_base + 197 (cluster_id * (unsigned)CLUSTER_SIZE) ); 193 198 194 199 unsigned int bloup = timer_address[XICU_REG(XICU_PTI_ACK, local_id)]; 200 bloup++; // to avoid a warning 195 201 #else 196 unsigned int* timer_address = (unsigned int*) &seg_tim_base +197 (cluster_id * CLUSTER_S PAN);202 unsigned int* timer_address = (unsigned int*)((char*)&seg_tim_base + 203 (cluster_id * CLUSTER_SIZE) ); 198 204 199 205 timer_address[local_id * TIMER_SPAN + TIMER_RESETIRQ] = 0; … … 258 264 } 259 265 260 unsigned int* tty_address = (unsigned int*)&seg_tty_base + tty_id*TTY_SPAN; 266 unsigned int* tty_address = (unsigned int*)( (char*)&seg_tty_base + 267 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 261 268 262 269 for (nwritten = 0; nwritten < length; nwritten++) 263 270 { 264 271 // check tty's status 265 if ((tty_address[ TTY_STATUS] & 0x2) == 0x2)272 if ((tty_address[tty_id*TTY_SPAN + TTY_STATUS] & 0x2) == 0x2) 266 273 break; 267 274 else 268 275 // write character 269 tty_address[ TTY_WRITE] = (unsigned int)buffer[nwritten];276 tty_address[tty_id*TTY_SPAN + TTY_WRITE] = (unsigned int)buffer[nwritten]; 270 277 } 271 278 return nwritten; 272 279 } 273 280 ////////////////////////////////////////////////////////////////////////////// 274 // _tty_read _irq()281 // _tty_read() 275 282 // This non-blocking function uses the TTY_GET_IRQ[tty_id] interrupt and 276 283 // the associated kernel buffer, that has been written by the ISR. 284 // It get the TTY terminal index from the context of the current task. 277 285 // It fetches one single character from the _tty_get_buf[tty_id] kernel 278 286 // buffer, writes this character to the user buffer, and resets the 279 287 // _tty_get_full[tty_id] buffer. 288 // The length argument is not used. 280 289 // Returns 0 if the kernel buffer is empty, 1 if the buffer is full. 281 290 ////////////////////////////////////////////////////////////////////////////// 282 unsigned int _tty_read _irq( char *buffer,283 291 unsigned int _tty_read( char *buffer, 292 unsigned int length) 284 293 { 285 294 unsigned int task_id = _get_current_task_id(); … … 304 313 } 305 314 //////////////////////////////////////////////////////////////////////////////// 306 // _tty_read() 307 // This non-blocking function fetches one character directly from the TTY_READ 308 // register of the TTY controler, and writes this character to the user buffer. 309 // It doesn't use the TTY_GET_IRQ interrupt and the associated kernel buffer. 310 // Returns 0 if the register is empty, 1 if the register is full. 311 //////////////////////////////////////////////////////////////////////////////// 312 unsigned int _tty_read( char *buffer, 313 unsigned int length) 314 { 315 unsigned int task_id = _get_current_task_id(); 316 unsigned int tty_id = _get_context_slot(task_id, CTX_TTY_ID); 317 318 if ( tty_id >= NB_TTYS ) 319 { 320 _tty_error( task_id ); 321 return 0; 322 } 323 324 unsigned int* tty_address = (unsigned int*)&seg_tty_base + tty_id*TTY_SPAN; 325 326 if ((tty_address[TTY_STATUS] & 0x1) != 0x1) 327 { 328 return 0; 329 } 330 else 331 { 332 *buffer = (char)tty_address[TTY_READ]; 333 return 1; 334 } 315 // _tty_get_char() 316 // This function is used by the _isr_tty to read a character in the TTY 317 // terminal defined by the tty_id argument. The character is stored 318 // in requested buffer, and the IRQ is acknowledged. 319 // Returns 0 if success, 1 if tty_id too large. 320 //////////////////////////////////////////////////////////////////////////////// 321 unsigned int _tty_get_char( unsigned int tty_id, 322 char* buffer ) 323 { 324 // checking argument 325 if ( tty_id >= NB_TTYS ) return 1; 326 327 // compute terminal base address 328 unsigned int *tty_address = (unsigned int*)( (char*)&seg_tty_base + 329 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 330 331 *buffer = (unsigned char)tty_address[tty_id*TTY_SPAN + TTY_READ]; 332 return 0; 335 333 } 336 334 … … 359 357 if ( proc_id >= NB_PROCS_MAX ) return 1; 360 358 361 unsigned int* icu_address = (unsigned int*) &seg_icu_base +362 (cluster_id * CLUSTER_SPAN);359 unsigned int* icu_address = (unsigned int*)( (char*)&seg_icu_base + 360 (cluster_id * (unsigned)CLUSTER_SIZE) ); 363 361 #if GIET_USE_XICU 364 362 if ( is_timer ) icu_address[XICU_REG(XICU_MSK_PTI_ENABLE, proc_id)] = value; … … 385 383 if ( proc_id >= NB_PROCS_MAX ) return 1; 386 384 387 unsigned int* icu_address = (unsigned int*) &seg_icu_base +388 (cluster_id * CLUSTER_SPAN);385 unsigned int* icu_address = (unsigned int*)( (char*)&seg_icu_base + 386 (cluster_id * (unsigned)CLUSTER_SIZE) ); 389 387 #if GIET_USE_XICU 390 388 unsigned int prio = icu_address[XICU_REG(XICU_PRIO, proc_id)]; … … 422 420 unsigned int value) 423 421 { 424 volatile unsigned int *gcd_address;425 426 422 // parameters checking 427 423 if (register_index >= GCD_END) 428 424 return 1; 429 425 430 gcd_address = (unsigned int*)&seg_gcd_base; 426 unsigned int* gcd_address = (unsigned int*)( (char*)&seg_gcd_base + 427 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 431 428 432 429 gcd_address[register_index] = value; // write word … … 441 438 unsigned int *buffer) 442 439 { 443 volatile unsigned int *gcd_address;444 445 440 // parameters checking 446 441 if (register_index >= GCD_END) 447 442 return 1; 448 443 449 gcd_address = (unsigned int*)&seg_gcd_base; 444 unsigned int* gcd_address = (unsigned int*)( (char*)&seg_gcd_base + 445 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 450 446 451 447 *buffer = gcd_address[register_index]; // read word … … 538 534 if ( (unsigned int)user_vaddr & 0x3 ) return 1; 539 535 540 unsigned int* ioc_address = (unsigned int*)&seg_ioc_base; 536 unsigned int* ioc_address = (unsigned int*)( (char*)&seg_ioc_base + 537 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 538 541 539 unsigned int block_size = ioc_address[BLOCK_DEVICE_BLOCK_SIZE]; 542 540 unsigned int length = count*block_size; … … 630 628 if ( GIET_IOMMU_ACTIVE ) 631 629 { 632 unsigned int* iob_address = (unsigned int*)&seg_iob_base; 630 unsigned int* iob_address = (unsigned int*)( (char*)&seg_iob_base + 631 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 633 632 634 633 for ( ix2 = 0 ; ix2 < _ioc_iommu_npages ; ix2++ ) … … 687 686 (unsigned int)buffer, 688 687 count ); 688 } 689 /////////////////////////////////////////////////////////////////////////////// 690 // _ioc_get_status() 691 // This function returns the transfert status, and acknowledge the IRQ. 692 // Returns 0 if success, > 0 if error. 693 /////////////////////////////////////////////////////////////////////////////// 694 unsigned int _ioc_get_status(unsigned int* status) 695 { 696 // get IOC base address 697 unsigned int* ioc_address = (unsigned int*)( (char*)&seg_ioc_base + 698 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 699 700 *status = ioc_address[BLOCK_DEVICE_STATUS]; // read status & reset IRQ 701 return 0; 689 702 } 690 703 … … 718 731 in_unckdata unsigned int _dma_iommu_npages[NB_DMAS_MAX * NB_CLUSTERS]; 719 732 #endif 733 734 ////////////////////////////////////////////////////////////////////////////////// 735 // _dma_reset_irq() 736 ////////////////////////////////////////////////////////////////////////////////// 737 unsigned int _dma_reset_irq( unsigned int cluster_id, 738 unsigned int local_id ) 739 { 740 // parameters checking 741 if ( cluster_id >= NB_CLUSTERS ) return 1; 742 if ( local_id >= NB_DMAS_MAX ) return 1; 743 744 // compute DMA base address 745 unsigned int* dma_address = (unsigned int*)( (char*)&seg_dma_base + 746 (cluster_id * (unsigned)CLUSTER_SIZE) ); 747 748 dma_address[local_id*DMA_SPAN + DMA_RESET] = 0; 749 return 0; 750 } 751 ////////////////////////////////////////////////////////////////////////////////// 752 // _dma_get_status() 753 ////////////////////////////////////////////////////////////////////////////////// 754 unsigned int _dma_get_status( unsigned int cluster_id, 755 unsigned int local_id, 756 unsigned int* status ) 757 { 758 // parameters checking 759 if ( cluster_id >= NB_CLUSTERS ) return 1; 760 if ( local_id >= NB_DMAS_MAX ) return 1; 761 762 // compute DMA base address 763 unsigned int* dma_address = (unsigned int*)( (char*)&seg_dma_base + 764 (cluster_id * (unsigned)CLUSTER_SIZE) ); 765 766 *status = dma_address[local_id*DMA_SPAN + DMA_LEN]; 767 return 0; 768 } 720 769 721 770 ////////////////////////////////////////////////////////////////////////////////// … … 819 868 unsigned int cluster_id = dma_id / NB_DMAS_MAX; 820 869 unsigned int loc_id = dma_id % NB_DMAS_MAX; 821 unsigned int* dma_base = (unsigned int*)&seg_dma_base + 822 (cluster_id * CLUSTER_SPAN) +823 ( loc_id * DMA_SPAN);824 870 871 unsigned int* dma_base = (unsigned int*)( (char*)&seg_dma_base + 872 (cluster_id * (unsigned)CLUSTER_SIZE) ); 873 825 874 // check user buffer address and length alignment 826 875 if ( (user_vaddr & 0x3) || (length & 0x3) ) … … 930 979 931 980 */ 981 932 982 // invalidate data cache in case of memory write 933 983 if ( to_user ) _dcache_buf_invalidate( (void*)user_vaddr, length ); … … 939 989 if ( to_user ) 940 990 { 941 dma_base[ DMA_SRC] = (unsigned int)fb_pbase;942 dma_base[ DMA_DST] = (unsigned int)user_pbase;991 dma_base[loc_id*DMA_SPAN + DMA_SRC] = (unsigned int)fb_pbase; 992 dma_base[loc_id*DMA_SPAN + DMA_DST] = (unsigned int)user_pbase; 943 993 } 944 994 else 945 995 { 946 dma_base[ DMA_SRC] = (unsigned int)user_pbase;947 dma_base[ DMA_DST] = (unsigned int)fb_pbase;948 } 949 dma_base[ DMA_LEN] = (unsigned int)length;996 dma_base[loc_id*DMA_SPAN + DMA_SRC] = (unsigned int)user_pbase; 997 dma_base[loc_id*DMA_SPAN + DMA_DST] = (unsigned int)fb_pbase; 998 } 999 dma_base[loc_id*DMA_SPAN + DMA_LEN] = (unsigned int)length; 950 1000 951 1001 return 0; … … 1011 1061 if ( GIET_IOMMU_ACTIVE ) 1012 1062 { 1013 unsigned int* iob_address = (unsigned int*)&seg_iob_base; 1063 unsigned int* iob_address = (unsigned int*)( (char*)&seg_iob_base + 1064 (CLUSTER_IO_ID * (unsigned)CLUSTER_SIZE) ); 1065 1014 1066 unsigned int ix1 = _dma_iommu_ix1 + dma_id; 1015 1067 unsigned int ix2;
Note: See TracChangeset
for help on using the changeset viewer.