![]() |
|
|||
File indexing completed on 2025-05-11 08:23:53
0001 /* SPDX-License-Identifier: BSD-2-Clause */ 0002 0003 /* 0004 * RTEMS support for MPC83xx 0005 * 0006 * This file contains the low level MPC83xx SPI driver parameters 0007 * and board-specific functions. 0008 */ 0009 0010 /* 0011 * Copyright (c) 2007 embedded brains GmbH & Co. KG 0012 * 0013 * Redistribution and use in source and binary forms, with or without 0014 * modification, are permitted provided that the following conditions 0015 * are met: 0016 * 1. Redistributions of source code must retain the above copyright 0017 * notice, this list of conditions and the following disclaimer. 0018 * 2. Redistributions in binary form must reproduce the above copyright 0019 * notice, this list of conditions and the following disclaimer in the 0020 * documentation and/or other materials provided with the distribution. 0021 * 0022 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 0023 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 0024 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 0025 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 0026 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 0027 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 0028 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 0029 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 0030 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 0031 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 0032 * POSSIBILITY OF SUCH DAMAGE. 0033 */ 0034 0035 #include <mpc83xx/mpc83xx_spidrv.h> 0036 #include <bsp/irq.h> 0037 #include <bsp.h> 0038 0039 #if defined(MPC83XX_BOARD_MPC8313ERDB) 0040 0041 #include <libchip/spi-sd-card.h> 0042 0043 #elif defined(MPC83XX_BOARD_MPC8349EAMDS) 0044 0045 #include <libchip/spi-flash-m25p40.h> 0046 0047 #elif defined(MPC83XX_BOARD_HSC_CM01) 0048 0049 #include <libchip/spi-fram-fm25l256.h> 0050 0051 #endif 0052 0053 /*=========================================================================*\ 0054 | Board-specific adaptation functions | 0055 \*=========================================================================*/ 0056 0057 /*=========================================================================*\ 0058 | Function: | 0059 \*-------------------------------------------------------------------------*/ 0060 static rtems_status_code bsp_spi_sel_addr 0061 ( 0062 /*-------------------------------------------------------------------------*\ 0063 | Purpose: | 0064 | address a slave device on the bus | 0065 +---------------------------------------------------------------------------+ 0066 | Input Parameters: | 0067 \*-------------------------------------------------------------------------*/ 0068 rtems_libi2c_bus_t *bh, /* bus specifier structure */ 0069 uint32_t addr, /* address to send on bus */ 0070 int rw /* 0=write,1=read */ 0071 ) 0072 /*-------------------------------------------------------------------------*\ 0073 | Return Value: | 0074 | o = ok or error code | 0075 \*=========================================================================*/ 0076 { 0077 0078 #if defined( MPC83XX_BOARD_MPC8313ERDB) 0079 0080 /* Check address */ 0081 if (addr > 0) { 0082 return RTEMS_INVALID_NUMBER; 0083 } 0084 0085 /* SCS (active low) */ 0086 mpc83xx.gpio [0].gpdat &= ~0x20000000; 0087 0088 #elif defined( MPC83XX_BOARD_MPC8349EAMDS) 0089 0090 /* 0091 * check device address for valid range 0092 */ 0093 if (addr > 0) { 0094 return RTEMS_INVALID_NUMBER; 0095 } 0096 /* 0097 * select given device 0098 * GPIO1[0] is nSEL_SPI for M25P40 0099 * set it to be active/low 0100 */ 0101 mpc83xx.gpio[0].gpdat &= ~(1 << (31- 0)); 0102 0103 #elif defined( MPC83XX_BOARD_HSC_CM01) 0104 0105 /* 0106 * check device address for valid range 0107 */ 0108 if (addr > 7) { 0109 return RTEMS_INVALID_NUMBER; 0110 } 0111 /* 0112 * select given device 0113 */ 0114 /* 0115 * GPIO1[24] is SPI_A0 0116 * GPIO1[25] is SPI_A1 0117 * GPIO1[26] is SPI_A2 0118 * set pins to address 0119 */ 0120 mpc83xx.gpio[0].gpdat = 0121 (mpc83xx.gpio[0].gpdat & ~(0x7 << (31-26))) 0122 | (addr << (31-26)); 0123 /* 0124 * GPIO1[27] is high-active strobe 0125 */ 0126 mpc83xx.gpio[0].gpdat |= (1 << (31- 27)); 0127 0128 #endif 0129 0130 return RTEMS_SUCCESSFUL; 0131 } 0132 0133 /*=========================================================================*\ 0134 | Function: | 0135 \*-------------------------------------------------------------------------*/ 0136 static rtems_status_code bsp_spi_send_start_dummy 0137 ( 0138 /*-------------------------------------------------------------------------*\ 0139 | Purpose: | 0140 | dummy function, SPI has no start condition | 0141 +---------------------------------------------------------------------------+ 0142 | Input Parameters: | 0143 \*-------------------------------------------------------------------------*/ 0144 rtems_libi2c_bus_t *bh /* bus specifier structure */ 0145 ) 0146 /*-------------------------------------------------------------------------*\ 0147 | Return Value: | 0148 | o = ok or error code | 0149 \*=========================================================================*/ 0150 { 0151 0152 #if defined( MPC83XX_BOARD_MPC8313ERDB) 0153 0154 /* SCS (inactive high) */ 0155 mpc83xx.gpio [0].gpdat |= 0x20000000; 0156 0157 #elif defined( MPC83XX_BOARD_MPC8349EAMDS) 0158 0159 /* 0160 * GPIO1[0] is nSEL_SPI for M25P40 0161 * set it to inactive/high 0162 */ 0163 mpc83xx.gpio[0].gpdat |= (1 << (31- 0)); 0164 0165 #elif defined( MPC83XX_BOARD_HSC_CM01) 0166 0167 /* 0168 * GPIO1[27] is high-active strobe 0169 * set it to inactive/ low 0170 */ 0171 mpc83xx.gpio[0].gpdat &= ~(0x1 << (31-27)); 0172 0173 #endif 0174 0175 return 0; 0176 } 0177 0178 /*=========================================================================*\ 0179 | Function: | 0180 \*-------------------------------------------------------------------------*/ 0181 static rtems_status_code bsp_spi_send_stop 0182 ( 0183 /*-------------------------------------------------------------------------*\ 0184 | Purpose: | 0185 | deselect SPI | 0186 +---------------------------------------------------------------------------+ 0187 | Input Parameters: | 0188 \*-------------------------------------------------------------------------*/ 0189 rtems_libi2c_bus_t *bh /* bus specifier structure */ 0190 ) 0191 /*-------------------------------------------------------------------------*\ 0192 | Return Value: | 0193 | o = ok or error code | 0194 \*=========================================================================*/ 0195 { 0196 #if defined(DEBUG) 0197 printk("bsp_spi_send_stop called... "); 0198 #endif 0199 0200 #if defined( MPC83XX_BOARD_MPC8313ERDB) 0201 0202 /* SCS (inactive high) */ 0203 mpc83xx.gpio [0].gpdat |= 0x20000000; 0204 0205 #elif defined( MPC83XX_BOARD_MPC8349EAMDS) 0206 0207 /* 0208 * deselect given device 0209 * GPIO1[0] is nSEL_SPI for M25P40 0210 * set it to be inactive/high 0211 */ 0212 mpc83xx.gpio[0].gpdat |= (1 << (31- 0)); 0213 0214 #elif defined( MPC83XX_BOARD_HSC_CM01) 0215 0216 /* 0217 * deselect device 0218 * GPIO1[27] is high-active strobe 0219 */ 0220 mpc83xx.gpio[0].gpdat &= ~(1 << (31- 27)); 0221 0222 #endif 0223 0224 #if defined(DEBUG) 0225 printk("... exit OK\r\n"); 0226 #endif 0227 return 0; 0228 } 0229 0230 /*=========================================================================*\ 0231 | list of handlers | 0232 \*=========================================================================*/ 0233 0234 rtems_libi2c_bus_ops_t bsp_spi_ops = { 0235 .init = mpc83xx_spi_init, 0236 .send_start = bsp_spi_send_start_dummy, 0237 .send_stop = bsp_spi_send_stop, 0238 .send_addr = bsp_spi_sel_addr, 0239 .read_bytes = mpc83xx_spi_read_bytes, 0240 .write_bytes = mpc83xx_spi_write_bytes, 0241 .ioctl = mpc83xx_spi_ioctl 0242 }; 0243 0244 static mpc83xx_spi_desc_t bsp_spi_bus_desc = { 0245 {/* public fields */ 0246 .ops = &bsp_spi_ops, 0247 .size = sizeof(bsp_spi_bus_desc) 0248 }, 0249 { /* our private fields */ 0250 .reg_ptr =&mpc83xx.spi, 0251 .initialized = FALSE, 0252 .irq_number = BSP_IPIC_IRQ_SPI, 0253 .base_frq = 0 /* filled in during init */ 0254 } 0255 }; 0256 0257 #ifdef MPC83XX_BOARD_MPC8313ERDB 0258 0259 #include <libchip/spi-sd-card.h> 0260 0261 #define SD_CARD_NUMBER 1 0262 0263 size_t sd_card_driver_table_size = SD_CARD_NUMBER; 0264 0265 sd_card_driver_entry sd_card_driver_table [SD_CARD_NUMBER] = { 0266 { 0267 .device_name = "/dev/sd-card-a", 0268 .bus = 0, 0269 .transfer_mode = SD_CARD_TRANSFER_MODE_DEFAULT, 0270 .command = SD_CARD_COMMAND_DEFAULT, 0271 /* .response = whatever, */ 0272 .response_index = SD_CARD_COMMAND_SIZE, 0273 .n_ac_max = SD_CARD_N_AC_MAX_DEFAULT, 0274 .block_number = 0, 0275 .block_size = 0, 0276 .block_size_shift = 0, 0277 .busy = true, 0278 .verbose = true, 0279 .schedule_if_busy = false 0280 } 0281 }; 0282 0283 #endif /* MPC83XX_BOARD_MPC8313ERDB */ 0284 0285 0286 /*=========================================================================*\ 0287 | initialization | 0288 \*=========================================================================*/ 0289 0290 /*=========================================================================*\ 0291 | Function: | 0292 \*-------------------------------------------------------------------------*/ 0293 rtems_status_code bsp_register_spi 0294 ( 0295 /*-------------------------------------------------------------------------*\ 0296 | Purpose: | 0297 | register SPI bus and devices | 0298 +---------------------------------------------------------------------------+ 0299 | Input Parameters: | 0300 \*-------------------------------------------------------------------------*/ 0301 void /* <none> */ 0302 ) 0303 /*-------------------------------------------------------------------------*\ 0304 | Return Value: | 0305 | 0 or error code | 0306 \*=========================================================================*/ 0307 { 0308 #if defined(MPC83XX_BOARD_MPC8313ERDB) 0309 rtems_status_code sc = RTEMS_SUCCESSFUL; 0310 #endif 0311 unsigned spi_busno; 0312 int ret_code; 0313 0314 /* 0315 * init I2C library (if not already done) 0316 */ 0317 rtems_libi2c_initialize (); 0318 0319 /* 0320 * init port pins used to address/select SPI devices 0321 */ 0322 0323 #if defined(MPC83XX_BOARD_MPC8313ERDB) 0324 0325 /* 0326 * Configured as master (direct connection to SD card) 0327 * 0328 * GPIO[28] : SOUT 0329 * GPIO[29] : SIN 0330 * GPIO[30] : SCLK 0331 * GPIO[02] : SCS (inactive high), GPIO[02] is normally connected to U43 at 0332 * pin 15 of MC74LCX244DT. 0333 */ 0334 0335 /* Function */ 0336 mpc83xx.syscon.sicrl = (mpc83xx.syscon.sicrl & ~0x03fc0000) | 0x30000000; 0337 0338 /* Direction */ 0339 mpc83xx.gpio [0].gpdir = (mpc83xx.gpio [0].gpdir & ~0x0000000f) | 0x2000000b; 0340 0341 /* Data */ 0342 mpc83xx.gpio [0].gpdat |= 0x20000000; 0343 0344 /* Open Drain */ 0345 /* mpc83xx.gpio [0].gpdr |= 0x0000000f; */ 0346 0347 #elif defined(MPC83XX_BOARD_MPC8349EAMDS) 0348 0349 /* 0350 * GPIO1[0] is nSEL_SPI for M25P40 0351 * set it to be output, high 0352 */ 0353 mpc83xx.gpio[0].gpdat |= (1 << (31- 0)); 0354 mpc83xx.gpio[0].gpdir |= (1 << (31- 0)); 0355 mpc83xx.gpio[0].gpdr &= ~(1 << (31- 0)); 0356 0357 #elif defined(MPC83XX_BOARD_HSC_CM01) 0358 0359 /* 0360 * GPIO1[24] is SPI_A0 0361 * GPIO1[25] is SPI_A1 0362 * GPIO1[26] is SPI_A2 0363 * GPIO1[27] is high-active strobe 0364 * set pins to be output, low 0365 */ 0366 mpc83xx.gpio[0].gpdat &= ~(0xf << (31-27)); 0367 mpc83xx.gpio[0].gpdir |= (0xf << (31-27)); 0368 mpc83xx.gpio[0].gpdr &= ~(0xf << (31-27)); 0369 0370 #else 0371 0372 /* 0373 * There is no SPI configuration information for this variant. 0374 */ 0375 (void) spi_busno; /* avoid set but not used warning */ 0376 #endif 0377 0378 /* 0379 * update base frequency in spi descriptor 0380 */ 0381 bsp_spi_bus_desc.softc.base_frq = BSP_bus_frequency; 0382 0383 /* 0384 * register SPI bus 0385 */ 0386 ret_code = rtems_libi2c_register_bus("/dev/spi", 0387 &(bsp_spi_bus_desc.bus_desc)); 0388 if (ret_code < 0) { 0389 return -ret_code; 0390 } 0391 spi_busno = (unsigned) ret_code; 0392 0393 #if defined(MPC83XX_BOARD_MPC8313ERDB) 0394 0395 /* Register SD Card driver */ 0396 sd_card_driver_table [0].bus = spi_busno; 0397 sc = sd_card_register(); 0398 if (sc != RTEMS_SUCCESSFUL) { 0399 return sc; 0400 } 0401 0402 #elif defined(MPC83XX_BOARD_MPC8349EAMDS) 0403 0404 /* 0405 * register M25P40 Flash 0406 */ 0407 ret_code = rtems_libi2c_register_drv(RTEMS_BSP_SPI_FLASH_DEVICE_NAME, 0408 spi_flash_m25p40_rw_driver_descriptor, 0409 spi_busno,0x00); 0410 #elif defined(MPC83XX_BOARD_HSC_CM01) 0411 0412 /* 0413 * register FM25L256 FRAM 0414 */ 0415 ret_code = rtems_libi2c_register_drv(RTEMS_BSP_SPI_FRAM_DEVICE_NAME, 0416 spi_fram_fm25l256_rw_driver_descriptor, 0417 spi_busno,0x02); 0418 0419 #endif 0420 0421 if (ret_code < 0) { 0422 return -ret_code; 0423 } 0424 0425 /* 0426 * FIXME: further drivers, when available 0427 */ 0428 return 0; 0429 }
[ Source navigation ] | [ Diff markup ] | [ Identifier search ] | [ general search ] |
This page was automatically generated by the 2.3.7 LXR engine. The LXR team |
![]() ![]() |