⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 gx_cat1025.c

📁 这是一个I2C的IP。直接拷到altera公司的相应软件的目录下
💻 C
字号:
#include <fcntl.h>
#define  __GLOBAL_DEF__

#include "sys/alt_dev.h"
#include "sys/alt_irq.h"
#include "sys/ioctl.h"
#include "sys/alt_errno.h"

#include "oc_i2c_master.h"

#define  I2C_SPEED    (400000u)  // 400kbps


int gx_cat1025_read(alt_fd* fd, char* ptr, int len)
{
  int count;
  
  gx_cat1025_dev* dev = (gx_cat1025_dev*) fd->dev;

  /* The parameters are valid */
  if(len <= 0 || fd == NULL || ptr == NULL)
  {
  	return -1;
  }

  /* The number of data could not be more than the capactity of CAT1025 */
  if(len > dev->capacity)
  {
  	  len = dev->capacity;
  }
  /*
   * When running in a multi threaded environment, obtain the "read_lock"
   * semaphore. This ensures that reading from the device is thread-safe.
   */

  ALT_SEM_PEND (dev->read_lock, 0);
/******** Implement Selective Read or Sequential Read timing *************/
  /* Send Slave address with start signal */
  I2C_SEND_BYTE_WITH_START(dev->base, dev->slave_addr);
  /* Send Byte address */
  I2C_SEND_BYTE(dev->base, dev->byte_addr);
  dev->byte_addr = 0;
  /* Send Slave address with start signal plus Read Command*/
  I2C_SEND_BYTE_WITH_START(dev->base, dev->slave_addr|0x01);
  /* if the length of data equals to 1 carry out byte read operation */
  if(1 == len)
  {
  	  *ptr = I2C_RECV_BYTE_WITH_STOP(dev->base);
  }
  else{
      for(count=0; count<len-1; count++)
      {
         ptr[count] = I2C_RECV_BYTE_WITH_ACK(dev->base);
      }
  }    
  ptr[count] = I2C_RECV_BYTE_WITH_STOP(dev->base);
   /*
   * Now that Read operation is complete, release the read
   * semaphore so that other threads can access the device.
   */

  ALT_SEM_POST (dev->read_lock);
  return len;
}


int gx_cat1025_write (alt_fd* fd, const char* ptr, int len)
{
  int block;
  int count;

  gx_cat1025_dev* dev = (gx_cat1025_dev*) fd->dev;
  
  /* The parameters are valid */
  if(len <= 0 || fd == NULL || ptr == NULL)
  {
  	return -1;
  }
  block = !(fd->fd_flags & O_NONBLOCK);
  /* The number of data could not be more than a page */
  if(len > dev->page_size)
  {
  	  len = dev->page_size;
  }
  count = len - 1;
  
  /*
   * When running in a multi threaded environment, obtain the "write_lock"
   * semaphore. This ensures that writing to the device is thread-safe.
   */

  ALT_SEM_PEND (dev->write_lock, 0);
/******** Implement Byte Write or Page Write timing *************/

  /* Send Slave address with start signal */
  I2C_SEND_BYTE_WITH_START(dev->base, dev->slave_addr);
  /* Send Byte address */
  I2C_SEND_BYTE(dev->base, dev->byte_addr);
   dev->byte_addr = 0;
  /* if the length of data equals to 1 carry out byte write operation */
  if(1 == len)
  {
  	  I2C_SEND_BYTE_WITH_STOP(dev->base, *ptr);
  }
  else { /* the length of data is more than 1, carry out page write operation */
      do{
       	   I2C_SEND_BYTE(dev->base, *ptr++);
       	   count--;     
      } while (block && count);
      //Send last byte with stop signal  
    	I2C_SEND_BYTE_WITH_STOP(dev->base, *ptr);
  }
  
   /*
   * Now that Write operation is complete, release the write
   * semaphore so that other threads can access the device.
   */

  ALT_SEM_POST (dev->write_lock);
  if (count)
  {
    ALT_ERRNO = EWOULDBLOCK;
  }
  
  return (len - count);
}


int gx_cat1025_lseek(alt_fd* fd, int ptr, int dir)
{
  int err = -1;
  gx_cat1025_dev* dev = (gx_cat1025_dev*) fd->dev;
  if(ptr > dev->capacity)
  {
     dev->byte_addr = ptr;
     err = 1;
  }
  return err;
  
}

void gx_cat1025_init(int base, gx_cat1025_dev* dev)
{
  
  alt_u32 prescale;
	// Calculate the prescale value
	prescale = dev->cpu_freq/((I2C_SPEED<<2) + I2C_SPEED);
  // Setup prescaler for the freq of SCL with sysclk of ALT_CPU_FREQ
  IOWR_OC_I2C_PRERLO(base, prescale & 0xff);
  IOWR_OC_I2C_PRERHI(base,(prescale & 0xff00)>>8);
  // Enable core and  disable interrupt
  IOWR_OC_I2C_CTR(base, 0x80);
  /* 
   * Initialise the read and write semaphores used to protect
   * access to the device when running in a multi-threaded environment.
   */
  ALT_SEM_CREATE (&dev->read_lock, 1);  
  ALT_SEM_CREATE (&dev->write_lock, 1);
  // register drivers into HAL
  alt_dev_reg(&dev->dev);
   
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -