Example #1
0
void Nhdc12832::refresh(void){
	Spi spi(spi_port);
	uint8_t buffer[MEM_ROWS];
	unsigned int i,j;
	unsigned char page = 0xB0;			//Page Address + 0xB0
	//cmd_out(0xAE);					//Display OFF
	cmd_out(0x40);					//Display start address + 0x40
	for(i=0;i<MEM_COLUMNS;i++){				//32pixel display / 8 pixels per page = 4 pages
		assert_cmd();
		buffer[0] = page;	//send page address
		buffer[1] = 0x10;	//column address upper 4 bits + 0x10
		buffer[2] = 0x00;	//column address lower 4 bits + 0x00
		assert_cs();
		spi.write(buffer, 3);
		deassert_cs();
		for(j=0;j<MEM_ROWS;j++){			//128 rows wide
			buffer[j] = nhd_mem[j][i];
		}
		assert_data();
		assert_cs();
		spi.write(buffer, MEM_ROWS);
		deassert_cs();
		page++;					//after 128 columns, go to next page
	}
	cmd_out(0xAF);					//Display ON
}
Example #2
0
int lcd_spi_complete_event(void * context, const void * data){
	int j;
	int i;

	//deassert CS each time a SPI event completes
	deassert_cs();

	i = lcd_page - 0xB0;
	if( i == LCD_COLS ){
		lcd_hold = 0x00;
		update_count(); //interrupt again on next timer match
		return 0; //all done
	}

	switch(lcd_write_state){
	case LCD_WRITE_PAGE:

		command_mode();
		lcd_buffer[0] = lcd_page;
		lcd_buffer[1] = 0x10;
		lcd_buffer[2] = 0x00;

		op.nbyte = 3;

		assert_cs();

		lcd_write_state = LCD_WRITE_DATA;
		hwpl_spi_write(context, &op);
		return 1;
	case LCD_WRITE_DATA:

		data_mode();
		assert_cs();

		for(j=0;j<LCD_ROWS;j++){			//128 rows high
			lcd_buffer[j] = mem[LCD_ROWS - j - 1][i];
		}

		op.nbyte = LCD_ROWS;

		lcd_page++;
		lcd_write_state = LCD_WRITE_PAGE;
		hwpl_spi_write(context, &op);
		break;
	}

	return 1;
}
Example #3
0
void Nhdc12832::cmd_out(unsigned char c){
	Spi spi(spi_port);
	assert_cmd();
	assert_cs();
	spi.swap(c);
	deassert_cs();
}
Example #4
0
void Nhdc12832::cmd_out(const void * cmd, int nbyte){
	Spi spi(spi_port);
	int i;
	const unsigned char * p = (const unsigned char*)cmd;
	assert_cmd();
	for(i=0; i < nbyte; i++){
		assert_cs();
		spi.swap(*p++);
		deassert_cs();
	}
}
Example #5
0
void Nhdc12832::data_out(const void * data, int nbyte){
	Spi spi(spi_port);
	int i;
	const char * p = (const char*)data;
	assert_data();
	for(i=0; i < nbyte; i++){
		assert_cs();
		spi.swap(*p++);
		deassert_cs();
	}
}
Example #6
0
static int jlink_spi_send_command(struct flashctx *flash, unsigned int writecnt, unsigned int readcnt,
		const unsigned char *writearr, unsigned char *readarr)
{
	uint32_t length;
	uint8_t *buffer;

	length = writecnt + readcnt;

	if (length > JTAG_MAX_TRANSFER_SIZE)
		return SPI_INVALID_LENGTH;

	buffer = malloc(length);

	if (!buffer) {
		msg_perr("Memory allocation failed.\n");
		return SPI_GENERIC_ERROR;
	}

	/* Reverse all bytes because the device transfers data LSB first. */
	reverse_bytes(buffer, writearr, writecnt);

	memset(buffer + writecnt, 0x00, readcnt);

	if (!assert_cs()) {
		free(buffer);
		return SPI_PROGRAMMER_ERROR;
	}

	int ret;

	ret = jaylink_jtag_io(jaylink_devh, buffer, buffer, buffer, length * 8, JAYLINK_JTAG_VERSION_2);

	if (ret != JAYLINK_OK) {
		msg_perr("jaylink_jag_io() failed: %s.\n", jaylink_strerror(ret));
		free(buffer);
		return SPI_PROGRAMMER_ERROR;
	}

	if (!deassert_cs()) {
		free(buffer);
		return SPI_PROGRAMMER_ERROR;
	}

	/* Reverse all bytes because the device transfers data LSB first. */
	reverse_bytes(readarr, buffer + writecnt, readcnt);
	free(buffer);

	return 0;
}
Example #7
0
//*****************************************************************************
// 
//!  The IntSpiGPIOHandler interrupt handler
//! 
//!  \param  none
//! 
//!  \return none
//! 
//!  \brief  GPIO A interrupt handler. When the external SSI WLAN device is
//!          ready to interact with Host CPU it generates an interrupt signal.
//!          After that Host CPU has registrated this interrupt request
//!          it set the corresponding /CS in active state.
// 
//*****************************************************************************
void CC3000InterruptHandler(void)
{
  if (sSpiInformation.ulSpiState == eSPI_STATE_POWERUP) {
    /* This means IRQ line was low call a callback of HCI Layer to inform on event */
    sSpiInformation.ulSpiState = eSPI_STATE_INITIALIZED;
  } else if (sSpiInformation.ulSpiState == eSPI_STATE_IDLE) {
    sSpiInformation.ulSpiState = eSPI_STATE_READ_IRQ;
    /* IRQ line goes down - start reception */
    assert_cs();
    SpiReadHeader();
    sSpiInformation.ulSpiState = eSPI_STATE_READ_EOT;
    SSIContReadOperation();
  } else if (sSpiInformation.ulSpiState == eSPI_STATE_WRITE_IRQ) {
    SpiWriteDataSynchronous(sSpiInformation.pTxPacket,
        sSpiInformation.usTxPacketLength);
    sSpiInformation.ulSpiState = eSPI_STATE_IDLE;
    negate_cs();
  }
}
Example #8
0
//*****************************************************************************
//
//! This function enter point for write flow
//!
//!  \param  buffer
//!
//!  \return none
//!
//!  \brief  ...
//
//*****************************************************************************
long SpiFirstWrite(unsigned char *ucBuf, unsigned short usLength)
{

  //
  // workaround for first transaction
  //
  assert_cs();

  delayMicroseconds(50);

  // SPI writes first 4 bytes of data
  SpiWriteDataSynchronous(ucBuf, 4);

  delayMicroseconds(50);

  SpiWriteDataSynchronous(ucBuf + 4, usLength - 4);

  sSpiInformation.ulSpiState = eSPI_STATE_IDLE;

  negate_cs();

  return (0);
}
Example #9
0
//*****************************************************************************
//
//! This function enter point for write flow
//!
//!  \param  buffer
//!
//!  \return none
//!
//!  \brief  ...
//
//*****************************************************************************
long SpiWrite(unsigned char *pUserBuffer, unsigned short usLength)
{
  unsigned char ucPad = 0;

  //
  // Figure out the total length of the packet in order to figure out if there is padding or not
  //
  if (!(usLength & 0x0001))
    ucPad++;

  pUserBuffer[0] = SPI_WRITE;
  pUserBuffer[1] = HI(usLength + ucPad);
  pUserBuffer[2] = LO(usLength + ucPad);
  pUserBuffer[3] = 0;
  pUserBuffer[4] = 0;

  usLength += (SPI_HEADER_SIZE + ucPad);

  // The magic number that resides at the end of the TX/RX buffer (1 byte after the allocated size)
  // for the purpose of overrun detection. If the magic number is overwritten - buffer overrun
  // occurred - and we will be stuck here forever!
  if (wlan_tx_buffer[CC3000_TX_BUFFER_SIZE - 1] != CC3000_BUFFER_MAGIC_NUMBER) {
    while (1);
  }

  if (sSpiInformation.ulSpiState == eSPI_STATE_POWERUP) {
    while (sSpiInformation.ulSpiState != eSPI_STATE_INITIALIZED);
  }

  if (sSpiInformation.ulSpiState == eSPI_STATE_INITIALIZED) {
    //
    // This is time for first TX/RX transactions over SPI: the IRQ is down - so need to send read buffer size command
    //
    SpiFirstWrite(pUserBuffer, usLength);
  } else {
    //
    // We need to prevent here race that can occur in case two back to back packets are sent to the
    // device, so the state will move to IDLE and once again to not IDLE due to IRQ
    //
    tSLInformation.WlanInterruptDisable();

    while (sSpiInformation.ulSpiState != eSPI_STATE_IDLE);

    sSpiInformation.ulSpiState = eSPI_STATE_WRITE_IRQ;
    sSpiInformation.pTxPacket = pUserBuffer;
    sSpiInformation.usTxPacketLength = usLength;

    //
    // Assert the CS line and wait till SSI IRQ line is active and then initialize write operation
    //
    assert_cs();

    //
    // Re-enable IRQ - if it was not disabled - this is not a problem...
    //
    tSLInformation.WlanInterruptEnable();

    //
    // check for a missing interrupt between the CS assertion and enabling back the interrupts
    //
    if (tSLInformation.ReadWlanInterruptPin() == 0) {
      SpiWriteDataSynchronous(sSpiInformation.pTxPacket,
          sSpiInformation.usTxPacketLength);

      sSpiInformation.ulSpiState = eSPI_STATE_IDLE;

      negate_cs();
    }
  }

  //
  // Due to the fact that we are currently implementing a blocking situation
  // here we will wait till end of transaction
  //

  while (eSPI_STATE_IDLE != sSpiInformation.ulSpiState);

  return (0);
}
Example #10
0
int lcd_ioctl(const device_cfg_t * cfg, int request, void * ctl){
	mlcd_attr_t * attr = (mlcd_attr_t*)ctl;
	tmr_action_t action;
	pio_attr_t pattr;
	device_periph_t p;

	switch(request){
	case I_MLCD_GETATTR:
		attr->freq = LCD_FREQ; //LCD updates 30 times per second
		attr->h = LCD_HEIGHT;
		attr->w = LCD_WIDTH;
		attr->size = LCD_ROWS * LCD_COLS;
		attr->mem = mem;
		attr->hold = lcd_hold;
		attr->rows = LCD_ROWS;
		attr->cols = LCD_COLS/4;
		attr->orientation = (ORIENT_BOTTOM)|(ORIENT_LEFT);
		break;

	case I_MLCD_CLEAR:
		memset(mem, 0, LCD_ROWS * LCD_COLS);
		lcd_hold = 0x80;
		break;

	case I_MLCD_HOLD:
		if( LCD_HOLD_COUNT() < 127 ){
			lcd_hold++;
		}
		break;

	case I_MLCD_RELEASE:
		if( LCD_HOLD_COUNT() > 0 ){
			lcd_hold--;
			LCD_TOUCH();
		}
		break;

	case I_MLCD_INIT:

		//initialize the IO -- chip select first
		pattr.mask = LCD_SPI_CS_PINMASK;
		pattr.mode = PIO_MODE_OUTPUT;
		p.port = LCD_SPI_CS_PORT;
		hwpl_pio_open((device_cfg_t*)&p);
		hwpl_pio_setattr(LCD_SPI_CS_PORT, &pattr);
		hwpl_pio_setmask(LCD_SPI_CS_PORT, (void*)LCD_SPI_CS_PINMASK);

		//Now A0
		pattr.mask = LCD_SPI_A0_PINMASK;
		if( p.port != LCD_SPI_A0_PORT ){
			p.port = LCD_SPI_A0_PORT;
			hwpl_pio_open((device_cfg_t*)&p);
		}
		hwpl_pio_setattr(LCD_SPI_A0_PORT, &pattr);
		hwpl_pio_setmask(LCD_SPI_A0_PORT, (void*)LCD_SPI_A0_PINMASK);

		//configure the timer to update the LCD
		action.channel = LCD_USECOND_OC;
		action.event = TMR_ACTION_EVENT_INTERRUPT;
		action.callback = lcd_usecond_match_event;
		action.context = (void*)cfg;
		hwpl_tmr_setaction(LCD_USECOND_TMR, &action);

		const char start[] = {0xA0, 0xAE, 0xC0, 0xA2, 0x2F, 0x21, 0x81, 0x2F};
		int i;
		const char * p = (const char*)start;

		command_mode();
		hwpl_pio_clrmask(LCD_SPI_A0_PORT, (void*)LCD_SPI_A0_PINMASK); //enter command mode

		for(i=0; i < 8; i++){
			assert_cs();
			hwpl_spi_swap(LCD_SPI_PORT, (void*)(uint32_t)(*p++));
			deassert_cs();
		}

		//start the timer update to refresh the screen
		update_count();
		break;

	case I_MLCD_ON:
		command_mode();
		assert_cs();
		hwpl_spi_swap(LCD_SPI_PORT, (void*)0xAF);
		deassert_cs();
		break;

	case I_MLCD_OFF:
		command_mode();
		assert_cs();
		hwpl_spi_swap(LCD_SPI_PORT, (void*)0xAE);
		deassert_cs();
		break;

	default:
		errno = EINVAL;
		return -1;
	}


	return 0;
}