ZG2100 Network interface source
Diff: drv/zg2100/zg_com.c
- Revision:
- 0:b802fc31f1db
- Child:
- 1:3a7c15057192
diff -r 000000000000 -r b802fc31f1db drv/zg2100/zg_com.c --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/drv/zg2100/zg_com.c Fri Jul 09 15:37:23 2010 +0000 @@ -0,0 +1,194 @@ + +/* +Copyright (c) 2010 Donatien Garnier (donatiengar [at] gmail [dot] com) + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +*/ + +#include "netCfg.h" +#if NET_ZG2100 + +#include "zg_defs.h" +#include "zg_com.h" + +#include "mbed.h" //For SPI, DigitalOut & InterruptIn + +//#define __DEBUG +#include "dbg/dbg.h" + +#define ZG_CMD_BUF_SIZE 16 + +//Locals +static SPI* m_pSpi; +static DigitalOut* m_pCs; +static InterruptIn* m_pInt; + +static byte cmd[ZG_CMD_BUF_SIZE] ZG_MEM; + +//Functions + +void zg_com_init(SPI* pSpi, DigitalOut* pCs, InterruptIn* pInt, DigitalOut* pNrst) +{ + m_pSpi = pSpi; + m_pCs = pCs; + m_pInt = pInt; + m_pCs->write(ZG_SPI_CS_OFF); //Do no select chip for now + m_pSpi->format(8,0); //8 bits / word, Mode 0 + //m_pSpi->frequency(1000000); //1Mhz - FMax is 25MHz + m_pSpi->frequency(20000000); //20Mhz - FMax is 25MHz + //Reset chip + pNrst->write(ZG_SPI_RST_ON); + wait_ms(100); + //And release + pNrst->write(ZG_SPI_RST_OFF); + m_pInt->fall(zg_on_int); //Attach on interrupt callback +} + + +//Registers Access + +uint32_t zg_register_read(uint32_t addr) +{ + int len; + uint32_t res; + + len = ZG_REG_LEN( addr ); + cmd[0] = (byte)(ZG_CMD_REG_RD | addr); + memset( &cmd[1], 0, len ); + + zg_spi_trf(cmd, len + 1); + + if(len==1) + { + res = cmd[1]; + } + else //if(len == 2) + { + res = (uint16_t) DTOHS( *((uint16_t*)&cmd[1]) ); + } + + return res; +} + +void zg_register_write(uint32_t addr, uint32_t reg) +{ + int len; + + len = ZG_REG_LEN( addr ); + cmd[0] = (byte)(ZG_CMD_REG_WR | addr); + + if(len==1) + { + cmd[1] = reg; + } + else //if(len == 2) + { + *((uint16_t*)&cmd[1]) = HTODS( reg ); + } + + zg_spi_trf(cmd, len + 1); +} + +//Indexed Registers Access + +uint32_t zg_indexed_register_read(uint32_t addr) +{ + zg_register_write( ZG_REG_IREG_ADDR, addr ); + return zg_register_read( ZG_REG_IREG_DATA ); +} + +void zg_indexed_register_write(uint32_t addr, uint32_t reg) +{ + zg_register_write( ZG_REG_IREG_ADDR, addr ); + zg_register_write( ZG_REG_IREG_DATA, reg ); +} + +//Fifos + +void zg_fifo_read( byte fifo, byte* pType, byte* pSubtype, byte* buf, int len ) +{ + cmd[0] = (fifo==ZG_FIFO_DATA)?ZG_CMD_FIFO_RD_DATA:ZG_CMD_FIFO_RD_MGMT; + memset( &cmd[1], 0, 2 ); + zg_spi_trf(cmd, 3, false); //false : Command not terminated yet + *pType = cmd[1]; + *pSubtype = cmd[2]; + + memset(buf, 0, len); + zg_spi_trf(buf, len); + + cmd[0] = ZG_CMD_FIFO_RD_DONE; + zg_spi_trf(cmd, 1); +} + +void zg_fifo_write( byte fifo, byte type, byte subtype, byte* buf, int len, bool start /*= true*/, bool stop /*= true*/ ) +{ + if(start) + { + cmd[0] = (fifo==ZG_FIFO_DATA)?ZG_CMD_FIFO_WR_DATA:ZG_CMD_FIFO_WR_MGMT; + cmd[1] = type; + cmd[2] = subtype; + zg_spi_trf(cmd, 3, false); //false : Command not terminated yet + } + + /*if(len>0 && buf!=NULL) + {*/ + zg_spi_trf(buf, len, stop); + /*}*/ + + if(stop) + { + cmd[0] = ZG_CMD_FIFO_WR_DONE; + zg_spi_trf(cmd, 1); + } +} + + +void zg_spi_trf(byte* buf, int len, bool resetCs /*= true*/) +{ + int i; + m_pCs->write(ZG_SPI_CS_ON); + +/* + DBG("\r\nDump: >>\r\n"); + for(i=0; i<len; i++) + { + DBG("%02x ", buf[i]); + } + DBG("\r\n>>\r\n"); +*/ + + for(i=0; i<len; i++) + { + buf[i] = (byte) m_pSpi->write(buf[i]); + } + +/* + DBG("\r\nDump: <<\r\n"); + for(i=0; i<len; i++) + { + DBG("%02x ", buf[i]); + } + DBG("\r\n<<\r\n"); +*/ + + if(resetCs) //If false, allows to split transfer in multiple calls + m_pCs->write(ZG_SPI_CS_OFF); +} + +#endif