mirror of
https://github.com/Spritetm/minimacplus.git
synced 2024-12-28 02:32:11 +00:00
Add mouse support, also add mipi component
This commit is contained in:
parent
dfce5c50be
commit
31c98d83b7
2
components/mipidisp/component.mk
Normal file
2
components/mipidisp/component.mk
Normal file
@ -0,0 +1,2 @@
|
||||
|
||||
COMPONENT_ADD_INCLUDEDIRS := .
|
91
components/mipidisp/crc16-ccitt.c
Normal file
91
components/mipidisp/crc16-ccitt.c
Normal file
@ -0,0 +1,91 @@
|
||||
/*
|
||||
* Copyright 2001-2010 Georges Menie (www.menie.org)
|
||||
* All rights reserved.
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* * Neither the name of the University of California, Berkeley nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND ANY
|
||||
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE REGENTS AND CONTRIBUTORS BE LIABLE FOR ANY
|
||||
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "crc16-ccitt.h"
|
||||
|
||||
/* CRC16 implementation acording to CCITT standards */
|
||||
|
||||
static const unsigned short crc16tab[256]= {
|
||||
0x0000,0x1021,0x2042,0x3063,0x4084,0x50a5,0x60c6,0x70e7,
|
||||
0x8108,0x9129,0xa14a,0xb16b,0xc18c,0xd1ad,0xe1ce,0xf1ef,
|
||||
0x1231,0x0210,0x3273,0x2252,0x52b5,0x4294,0x72f7,0x62d6,
|
||||
0x9339,0x8318,0xb37b,0xa35a,0xd3bd,0xc39c,0xf3ff,0xe3de,
|
||||
0x2462,0x3443,0x0420,0x1401,0x64e6,0x74c7,0x44a4,0x5485,
|
||||
0xa56a,0xb54b,0x8528,0x9509,0xe5ee,0xf5cf,0xc5ac,0xd58d,
|
||||
0x3653,0x2672,0x1611,0x0630,0x76d7,0x66f6,0x5695,0x46b4,
|
||||
0xb75b,0xa77a,0x9719,0x8738,0xf7df,0xe7fe,0xd79d,0xc7bc,
|
||||
0x48c4,0x58e5,0x6886,0x78a7,0x0840,0x1861,0x2802,0x3823,
|
||||
0xc9cc,0xd9ed,0xe98e,0xf9af,0x8948,0x9969,0xa90a,0xb92b,
|
||||
0x5af5,0x4ad4,0x7ab7,0x6a96,0x1a71,0x0a50,0x3a33,0x2a12,
|
||||
0xdbfd,0xcbdc,0xfbbf,0xeb9e,0x9b79,0x8b58,0xbb3b,0xab1a,
|
||||
0x6ca6,0x7c87,0x4ce4,0x5cc5,0x2c22,0x3c03,0x0c60,0x1c41,
|
||||
0xedae,0xfd8f,0xcdec,0xddcd,0xad2a,0xbd0b,0x8d68,0x9d49,
|
||||
0x7e97,0x6eb6,0x5ed5,0x4ef4,0x3e13,0x2e32,0x1e51,0x0e70,
|
||||
0xff9f,0xefbe,0xdfdd,0xcffc,0xbf1b,0xaf3a,0x9f59,0x8f78,
|
||||
0x9188,0x81a9,0xb1ca,0xa1eb,0xd10c,0xc12d,0xf14e,0xe16f,
|
||||
0x1080,0x00a1,0x30c2,0x20e3,0x5004,0x4025,0x7046,0x6067,
|
||||
0x83b9,0x9398,0xa3fb,0xb3da,0xc33d,0xd31c,0xe37f,0xf35e,
|
||||
0x02b1,0x1290,0x22f3,0x32d2,0x4235,0x5214,0x6277,0x7256,
|
||||
0xb5ea,0xa5cb,0x95a8,0x8589,0xf56e,0xe54f,0xd52c,0xc50d,
|
||||
0x34e2,0x24c3,0x14a0,0x0481,0x7466,0x6447,0x5424,0x4405,
|
||||
0xa7db,0xb7fa,0x8799,0x97b8,0xe75f,0xf77e,0xc71d,0xd73c,
|
||||
0x26d3,0x36f2,0x0691,0x16b0,0x6657,0x7676,0x4615,0x5634,
|
||||
0xd94c,0xc96d,0xf90e,0xe92f,0x99c8,0x89e9,0xb98a,0xa9ab,
|
||||
0x5844,0x4865,0x7806,0x6827,0x18c0,0x08e1,0x3882,0x28a3,
|
||||
0xcb7d,0xdb5c,0xeb3f,0xfb1e,0x8bf9,0x9bd8,0xabbb,0xbb9a,
|
||||
0x4a75,0x5a54,0x6a37,0x7a16,0x0af1,0x1ad0,0x2ab3,0x3a92,
|
||||
0xfd2e,0xed0f,0xdd6c,0xcd4d,0xbdaa,0xad8b,0x9de8,0x8dc9,
|
||||
0x7c26,0x6c07,0x5c64,0x4c45,0x3ca2,0x2c83,0x1ce0,0x0cc1,
|
||||
0xef1f,0xff3e,0xcf5d,0xdf7c,0xaf9b,0xbfba,0x8fd9,0x9ff8,
|
||||
0x6e17,0x7e36,0x4e55,0x5e74,0x2e93,0x3eb2,0x0ed1,0x1ef0
|
||||
};
|
||||
|
||||
static int invert(int d) {
|
||||
int q=0;
|
||||
if (d&0x01) q|=0x80;
|
||||
if (d&0x02) q|=0x40;
|
||||
if (d&0x04) q|=0x20;
|
||||
if (d&0x08) q|=0x10;
|
||||
if (d&0x10) q|=0x08;
|
||||
if (d&0x20) q|=0x04;
|
||||
if (d&0x40) q|=0x02;
|
||||
if (d&0x80) q|=0x01;
|
||||
return q;
|
||||
}
|
||||
|
||||
unsigned short crc16_ccitt(uint16_t oldcrc, const void *buf, int len)
|
||||
{
|
||||
register int counter;
|
||||
register unsigned short crc = oldcrc;
|
||||
for( counter = 0; counter < len; counter++) {
|
||||
char d=*(char *)buf++;
|
||||
char q=invert(d);
|
||||
crc = (crc<<8) ^ crc16tab[((crc>>8) ^ q)&0x00FF];
|
||||
}
|
||||
|
||||
return (invert(crc>>8))|(invert(crc&0xff)<<8);
|
||||
}
|
35
components/mipidisp/crc16-ccitt.h
Normal file
35
components/mipidisp/crc16-ccitt.h
Normal file
@ -0,0 +1,35 @@
|
||||
/*
|
||||
* Copyright 2001-2010 Georges Menie (www.menie.org)
|
||||
* All rights reserved.
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* * Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* * Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* * Neither the name of the University of California, Berkeley nor the
|
||||
* names of its contributors may be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND ANY
|
||||
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE REGENTS AND CONTRIBUTORS BE LIABLE FOR ANY
|
||||
* DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#ifndef _CRC16_H_
|
||||
#define _CRC16_H_
|
||||
|
||||
|
||||
#include <stdint.h>
|
||||
unsigned short crc16_ccitt(uint16_t oldcrc, const void *buf, int len);
|
||||
|
||||
#endif /* _CRC16_H_ */
|
52
components/mipidisp/hexdump.c
Normal file
52
components/mipidisp/hexdump.c
Normal file
@ -0,0 +1,52 @@
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
void hexdump (void *addr, int len) {
|
||||
int i;
|
||||
unsigned char buff[17];
|
||||
unsigned char *pc = (unsigned char*)addr;
|
||||
|
||||
|
||||
if (len == 0) {
|
||||
printf(" ZERO LENGTH\n");
|
||||
return;
|
||||
}
|
||||
if (len < 0) {
|
||||
printf(" NEGATIVE LENGTH: %i\n",len);
|
||||
return;
|
||||
}
|
||||
|
||||
// Process every byte in the data.
|
||||
for (i = 0; i < len; i++) {
|
||||
// Multiple of 16 means new line (with line offset).
|
||||
|
||||
if ((i % 16) == 0) {
|
||||
// Just don't print ASCII for the zeroth line.
|
||||
if (i != 0)
|
||||
printf (" %s\n", buff);
|
||||
|
||||
// Output the offset.
|
||||
printf (" %04x ", i);
|
||||
}
|
||||
|
||||
// Now the hex code for the specific character.
|
||||
printf (" %02x", pc[i]);
|
||||
|
||||
// And store a printable ASCII character for later.
|
||||
if ((pc[i] < 0x20) || (pc[i] > 0x7e))
|
||||
buff[i % 16] = '.';
|
||||
else
|
||||
buff[i % 16] = pc[i];
|
||||
buff[(i % 16) + 1] = '\0';
|
||||
}
|
||||
|
||||
// Pad out last line if not exactly 16 characters.
|
||||
while ((i % 16) != 0) {
|
||||
printf (" ");
|
||||
i++;
|
||||
}
|
||||
|
||||
// And print the final ASCII bit.
|
||||
printf (" %s\n", buff);
|
||||
}
|
2
components/mipidisp/hexdump.h
Normal file
2
components/mipidisp/hexdump.h
Normal file
@ -0,0 +1,2 @@
|
||||
void hexdump (void *addr, int len);
|
||||
|
299
components/mipidisp/mipi.c
Normal file
299
components/mipidisp/mipi.c
Normal file
@ -0,0 +1,299 @@
|
||||
#if 1
|
||||
/*
|
||||
Thing to emulate single-lane MIPI using a flipflop and a bunch of resistors.
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "freertos/semphr.h"
|
||||
#include "esp_system.h"
|
||||
#include "driver/spi_common.h"
|
||||
#include "soc/gpio_struct.h"
|
||||
#include "soc/spi_struct.h"
|
||||
#include "soc/spi_reg.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "esp_heap_alloc_caps.h"
|
||||
#include "mipi.h"
|
||||
#include "hexdump.h"
|
||||
|
||||
//IO pins
|
||||
#define GPIO_D0N_LS 4
|
||||
#define GPIO_D0P_LS 33
|
||||
#define GPIO_D0_HS 32
|
||||
#define GPIO_CLKP_LS 25
|
||||
#define GPIO_CLKN_LS 27
|
||||
#define GPIO_FF_NRST 14
|
||||
#define GPIO_FF_CLK 12
|
||||
#define GPIO_NRST 5
|
||||
|
||||
|
||||
|
||||
#define HOST VSPI_HOST
|
||||
#define IRQSRC ETS_SPI3_DMA_INTR_SOURCE
|
||||
#define DMACH 2
|
||||
#define DESCCNT 8
|
||||
|
||||
#define SOTEOTWAIT() asm volatile("nop; nop; nop; nop")
|
||||
//#define SOTEOTWAIT() ets_delay_us(10);
|
||||
|
||||
static spi_dev_t *spidev;
|
||||
static int cur_idle_desc=0;
|
||||
static lldesc_t idle_dmadesc[3];
|
||||
static lldesc_t data_dmadesc[DESCCNT];
|
||||
static SemaphoreHandle_t sem=NULL;
|
||||
|
||||
//ToDo: move these to spi_common...
|
||||
|
||||
static int spi_freq_for_pre_n(int fapb, int pre, int n) {
|
||||
return (fapb / (pre * n));
|
||||
}
|
||||
/*
|
||||
* Set the SPI clock to a certain frequency. Returns the effective frequency set, which may be slightly
|
||||
* different from the requested frequency.
|
||||
*/
|
||||
static int spi_set_clock(spi_dev_t *hw, int fapb, int hz, int duty_cycle) {
|
||||
int pre, n, h, l, eff_clk;
|
||||
|
||||
//In hw, n, h and l are 1-64, pre is 1-8K. Value written to register is one lower than used value.
|
||||
if (hz>((fapb/4)*3)) {
|
||||
//Using Fapb directly will give us the best result here.
|
||||
hw->clock.clkcnt_l=0;
|
||||
hw->clock.clkcnt_h=0;
|
||||
hw->clock.clkcnt_n=0;
|
||||
hw->clock.clkdiv_pre=0;
|
||||
hw->clock.clk_equ_sysclk=1;
|
||||
eff_clk=fapb;
|
||||
} else {
|
||||
//For best duty cycle resolution, we want n to be as close to 32 as possible, but
|
||||
//we also need a pre/n combo that gets us as close as possible to the intended freq.
|
||||
//To do this, we bruteforce n and calculate the best pre to go along with that.
|
||||
//If there's a choice between pre/n combos that give the same result, use the one
|
||||
//with the higher n.
|
||||
int bestn=-1;
|
||||
int bestpre=-1;
|
||||
int besterr=0;
|
||||
int errval;
|
||||
for (n=2; n<=64; n++) { //Start at 2: we need to be able to set h/l so we have at least one high and one low pulse.
|
||||
//Effectively, this does pre=round((fapb/n)/hz).
|
||||
pre=((fapb/n)+(hz/2))/hz;
|
||||
if (pre<=0) pre=1;
|
||||
if (pre>8192) pre=8192;
|
||||
errval=abs(spi_freq_for_pre_n(fapb, pre, n)-hz);
|
||||
if (bestn==-1 || errval<=besterr) {
|
||||
besterr=errval;
|
||||
bestn=n;
|
||||
bestpre=pre;
|
||||
}
|
||||
}
|
||||
|
||||
n=bestn;
|
||||
pre=bestpre;
|
||||
l=n;
|
||||
//This effectively does round((duty_cycle*n)/256)
|
||||
h=(duty_cycle*n+127)/256;
|
||||
if (h<=0) h=1;
|
||||
|
||||
hw->clock.clk_equ_sysclk=0;
|
||||
hw->clock.clkcnt_n=n-1;
|
||||
hw->clock.clkdiv_pre=pre-1;
|
||||
hw->clock.clkcnt_h=h-1;
|
||||
hw->clock.clkcnt_l=l-1;
|
||||
eff_clk=spi_freq_for_pre_n(fapb, pre, n);
|
||||
}
|
||||
return eff_clk;
|
||||
}
|
||||
|
||||
static void spidma_intr(void *arg) {
|
||||
BaseType_t xHigherPriorityTaskWoken=0;
|
||||
spidev->dma_int_clr.val=0xFFFFFFFF; //clear all ints
|
||||
//Data is sent
|
||||
// ets_printf("int\n");
|
||||
|
||||
xSemaphoreGiveFromISR(sem, &xHigherPriorityTaskWoken);
|
||||
if (xHigherPriorityTaskWoken) portYIELD_FROM_ISR();
|
||||
}
|
||||
|
||||
/*
|
||||
Brings up the clock and data lines to LP11, resyncs the flipflop, restarts the clock and DMA engine.
|
||||
*/
|
||||
void mipiResync() {
|
||||
//Get clock and data transceivers back in idle state
|
||||
// gpio_set_level(GPIO_D0N_LS, 1);
|
||||
// SOTEOTWAIT();
|
||||
// gpio_set_level(GPIO_D0P_LS, 1);
|
||||
|
||||
gpio_set_level(GPIO_CLKN_LS, 1);
|
||||
SOTEOTWAIT();
|
||||
gpio_set_level(GPIO_CLKP_LS, 1);
|
||||
|
||||
//Stop DMA transfer
|
||||
spidev->dma_conf.dma_tx_stop=1;
|
||||
while (spidev->ext2.val!=0) ;
|
||||
|
||||
//Clear flipflop
|
||||
gpio_set_level(GPIO_FF_NRST, 0);
|
||||
ets_delay_us(1);
|
||||
gpio_set_level(GPIO_FF_NRST, 1);
|
||||
|
||||
//Clock is in LP11 now. We should go LP01, LP00 to enable HS receivers
|
||||
gpio_set_level(GPIO_CLKP_LS, 0);
|
||||
SOTEOTWAIT();
|
||||
gpio_set_level(GPIO_CLKN_LS, 0);
|
||||
|
||||
cur_idle_desc=0;
|
||||
idle_dmadesc[0].qe.stqe_next=&idle_dmadesc[0];
|
||||
//Set SPI to transfer contents of idle dmadesc
|
||||
spidev->dma_conf.val |= SPI_OUT_RST|SPI_IN_RST|SPI_AHBM_RST|SPI_AHBM_FIFO_RST;
|
||||
spidev->dma_out_link.start=0;
|
||||
spidev->dma_in_link.start=0;
|
||||
spidev->dma_conf.val &= ~(SPI_OUT_RST|SPI_IN_RST|SPI_AHBM_RST|SPI_AHBM_FIFO_RST);
|
||||
spidev->dma_conf.dma_tx_stop=0;
|
||||
spidev->dma_conf.dma_continue=1;
|
||||
spidev->dma_conf.out_data_burst_en=1;
|
||||
spidev->user.usr_mosi_highpart=0;
|
||||
spidev->dma_out_link.addr=(int)(&idle_dmadesc[0]) & 0xFFFFF;
|
||||
spidev->dma_out_link.start=1;
|
||||
spidev->user.usr_mosi=1;
|
||||
spidev->cmd.usr=1;
|
||||
|
||||
//Data pair is in LP11 now. We should go LP01, LP00 to enable HS receivers
|
||||
// gpio_set_level(GPIO_D0P_LS, 0);
|
||||
// SOTEOTWAIT();
|
||||
// gpio_set_level(GPIO_D0N_LS, 0);
|
||||
|
||||
}
|
||||
void mipiInit() {
|
||||
esp_err_t ret;
|
||||
bool io_native=false;
|
||||
spi_bus_config_t buscfg={
|
||||
.miso_io_num=-1,
|
||||
.mosi_io_num=GPIO_D0_HS,
|
||||
.sclk_io_num=GPIO_FF_CLK,
|
||||
.quadwp_io_num=-1,
|
||||
.quadhd_io_num=-1,
|
||||
.max_transfer_sz=4096*3
|
||||
};
|
||||
|
||||
gpio_config_t io_conf={
|
||||
.intr_type=GPIO_INTR_DISABLE,
|
||||
.mode=GPIO_MODE_OUTPUT,
|
||||
.pin_bit_mask=(1<<GPIO_D0N_LS)|(1LL<<GPIO_D0P_LS)|(1LL<<GPIO_D0_HS)|(1<<GPIO_CLKP_LS)|
|
||||
(1<<GPIO_CLKN_LS)|(1<<GPIO_FF_NRST)|(1<<GPIO_FF_CLK)|(1<<GPIO_NRST),
|
||||
};
|
||||
gpio_config(&io_conf);
|
||||
|
||||
assert(spicommon_periph_claim(HOST));
|
||||
ret=spicommon_bus_initialize_io(HOST, &buscfg, DMACH, SPICOMMON_BUSFLAG_MASTER, &io_native);
|
||||
assert(ret==ESP_OK);
|
||||
spidev=spicommon_hw_for_host(HOST);
|
||||
|
||||
//Set up idle dma desc
|
||||
uint8_t *idle_mem=pvPortMallocCaps(64, MALLOC_CAP_DMA);
|
||||
memset(idle_mem, 0, 64);
|
||||
for (int i=0; i<3; i++) {
|
||||
idle_dmadesc[i].size=64;
|
||||
idle_dmadesc[i].length=64;
|
||||
idle_dmadesc[i].buf=idle_mem;
|
||||
idle_dmadesc[i].eof=0;
|
||||
idle_dmadesc[i].sosf=0;
|
||||
idle_dmadesc[i].owner=1;
|
||||
idle_dmadesc[i].qe.stqe_next = &idle_dmadesc[i];
|
||||
}
|
||||
|
||||
esp_intr_alloc(IRQSRC, 0, spidma_intr, NULL, NULL);
|
||||
|
||||
//Reset DMA
|
||||
spidev->dma_conf.val|=SPI_OUT_RST|SPI_IN_RST|SPI_AHBM_RST|SPI_AHBM_FIFO_RST;
|
||||
spidev->dma_out_link.start=0;
|
||||
spidev->dma_in_link.start=0;
|
||||
spidev->dma_conf.val&=~(SPI_OUT_RST|SPI_IN_RST|SPI_AHBM_RST|SPI_AHBM_FIFO_RST);
|
||||
//Reset timing
|
||||
spidev->ctrl2.val=0;
|
||||
spi_set_clock(spidev, 80000000, 20000000, 128);
|
||||
|
||||
//Configure SPI host
|
||||
spidev->ctrl.rd_bit_order=1; //LSB first
|
||||
spidev->ctrl.wr_bit_order=1;
|
||||
spidev->pin.ck_idle_edge=0;
|
||||
spidev->user.ck_out_edge=0;
|
||||
spidev->ctrl2.miso_delay_mode=2;
|
||||
spidev->ctrl.val &= ~(SPI_FREAD_DUAL|SPI_FREAD_QUAD|SPI_FREAD_DIO|SPI_FREAD_QIO);
|
||||
spidev->user.val &= ~(SPI_FWRITE_DUAL|SPI_FWRITE_QUAD|SPI_FWRITE_DIO|SPI_FWRITE_QIO);
|
||||
|
||||
//Disable unneeded ints
|
||||
spidev->slave.val=0;
|
||||
spidev->dma_int_ena.val=0;
|
||||
//Set int on EOF
|
||||
spidev->dma_int_clr.val=0xFFFFFFFF; //clear all ints
|
||||
spidev->dma_int_ena.out_eof=1;
|
||||
// spidev->dma_int_ena.in_suc_eof=1;
|
||||
|
||||
//Init GPIO to MIPI idle levels
|
||||
gpio_set_level(GPIO_D0N_LS, 1);
|
||||
gpio_set_level(GPIO_D0P_LS, 1);
|
||||
gpio_set_level(GPIO_CLKN_LS, 1);
|
||||
gpio_set_level(GPIO_CLKP_LS, 1);
|
||||
|
||||
//Reset display
|
||||
gpio_set_level(GPIO_NRST, 0);
|
||||
ets_delay_us(200);
|
||||
gpio_set_level(GPIO_NRST, 1);
|
||||
//Wait till display lives
|
||||
vTaskDelay(100/portTICK_RATE_MS);
|
||||
|
||||
sem=xSemaphoreCreateBinary();
|
||||
// xSemaphoreGive(sem);
|
||||
mipiResync(0);
|
||||
|
||||
}
|
||||
|
||||
void mipiSendMultiple(uint8_t **data, int *lengths, int count) {
|
||||
esp_err_t ret;
|
||||
if (count==0) return; //no need to send anything
|
||||
assert(data[0][0]==0xB8);
|
||||
// hexdump(data, count);
|
||||
//Set up link to new transfer
|
||||
int next_idle_desc=(cur_idle_desc==0)?1:0;
|
||||
|
||||
int last=-1;
|
||||
for (int i=0; i<count; i++) {
|
||||
last++;
|
||||
spicommon_setup_dma_desc_links(&data_dmadesc[last], lengths[i], data[i], false);
|
||||
//Look for new end
|
||||
for (; data_dmadesc[last].eof!=1; last++) ;
|
||||
//Kill eof and make desc point to the next one.
|
||||
data_dmadesc[last].eof=0;
|
||||
data_dmadesc[last].qe.stqe_next=&data_dmadesc[last+1];
|
||||
}
|
||||
//Make very last data desc go to the runout idle desc
|
||||
data_dmadesc[last].qe.stqe_next=&idle_dmadesc[2];
|
||||
//and make the runout go to the end idle desc
|
||||
idle_dmadesc[2].qe.stqe_next=&idle_dmadesc[next_idle_desc];
|
||||
idle_dmadesc[2].eof=1;
|
||||
//Make sure that idle desc keeps spinning
|
||||
idle_dmadesc[next_idle_desc].qe.stqe_next=&idle_dmadesc[next_idle_desc];
|
||||
|
||||
gpio_set_level(GPIO_D0P_LS, 0);
|
||||
SOTEOTWAIT();
|
||||
gpio_set_level(GPIO_D0N_LS, 0);
|
||||
|
||||
//Break the loop on the current idle descriptor
|
||||
idle_dmadesc[cur_idle_desc].qe.stqe_next=&data_dmadesc[0];
|
||||
//Okay, done.
|
||||
cur_idle_desc=next_idle_desc; //for next time
|
||||
|
||||
//Wait until transmission is done
|
||||
xSemaphoreTake(sem, portMAX_DELAY);
|
||||
|
||||
gpio_set_level(GPIO_D0N_LS, 1);
|
||||
SOTEOTWAIT();
|
||||
gpio_set_level(GPIO_D0P_LS, 1);
|
||||
}
|
||||
|
||||
void mipiSend(uint8_t *data, int len) {
|
||||
mipiSendMultiple(&data, &len, 1);
|
||||
}
|
||||
|
||||
#endif
|
11
components/mipidisp/mipi.h
Normal file
11
components/mipidisp/mipi.h
Normal file
@ -0,0 +1,11 @@
|
||||
#ifndef MIPI_H
|
||||
#define MIPI_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
void mipiSend(uint8_t *data, int count);
|
||||
void mipiSendMultiple(uint8_t **data, int *lengths, int count);
|
||||
void mipiInit();
|
||||
void mipiResync();
|
||||
|
||||
#endif
|
85
components/mipidisp/mipi_dsi.c
Normal file
85
components/mipidisp/mipi_dsi.c
Normal file
@ -0,0 +1,85 @@
|
||||
#include <stdio.h>
|
||||
#include <alloca.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <rom/crc.h>
|
||||
#include "crc16-ccitt.h"
|
||||
#include "mipi.h"
|
||||
|
||||
//Reminder; MIPI is very LSB-first.
|
||||
typedef struct {
|
||||
uint8_t sot; //should be 0xB8
|
||||
uint8_t datatype;
|
||||
uint16_t wordcount;
|
||||
uint8_t ecc; //0
|
||||
uint8_t data[];
|
||||
//Footer is 2 bytes of checksum.
|
||||
} __attribute__((packed)) DsiLPHdr;
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t sot; //should be 0xB8
|
||||
uint8_t datatype;
|
||||
uint8_t data[];
|
||||
//Footer is 1 byte of ECC
|
||||
} __attribute__((packed)) DsiSPHdr;
|
||||
|
||||
|
||||
// calc XOR parity bit of all '1's in 24 bit value
|
||||
static char parity (uint32_t val) {
|
||||
uint32_t i,p;
|
||||
p=0;
|
||||
for(i=0; i!=24; i++) {
|
||||
p^=val;
|
||||
val>>=1;
|
||||
}
|
||||
return (p&1);
|
||||
}
|
||||
|
||||
static uint8_t calc_ecc(uint8_t *buf) {
|
||||
int ret=0;
|
||||
uint32_t cmd=(buf[0])+(buf[1]<<8)+(buf[2]<<16);
|
||||
if(parity(cmd & 0b111100010010110010110111)) ret|=0x01;
|
||||
if(parity(cmd & 0b111100100101010101011011)) ret|=0x02;
|
||||
if(parity(cmd & 0b011101001001101001101101)) ret|=0x04;
|
||||
if(parity(cmd & 0b101110001110001110001110)) ret|=0x08;
|
||||
if(parity(cmd & 0b110111110000001111110000)) ret|=0x10;
|
||||
if(parity(cmd & 0b111011111111110000000000)) ret|=0x20;
|
||||
return ret;
|
||||
}
|
||||
|
||||
static uint16_t mipiword(uint16_t val) {
|
||||
uint16_t ret;
|
||||
uint8_t *pret=(uint8_t*)&ret;
|
||||
pret[0]=(val&0xff);
|
||||
pret[1]=(val>>8);
|
||||
return ret;
|
||||
}
|
||||
|
||||
//Warning: CRC isn't tested (my display does not use it)
|
||||
void mipiDsiSendLong(int type, uint8_t *data, int len) {
|
||||
DsiLPHdr p;
|
||||
uint8_t footer[3];
|
||||
uint8_t *datas[3]={(uint8_t*)&p, data, footer};
|
||||
int lengths[3]={sizeof(DsiLPHdr), len, sizeof(footer)};
|
||||
|
||||
p.sot=0xB8;
|
||||
p.datatype=type;
|
||||
p.wordcount=mipiword(len);
|
||||
p.ecc=calc_ecc((uint8_t*)&p.datatype);
|
||||
int crc=crc16_ccitt(0xFFFF, data, len);
|
||||
footer[0]=(crc&0xff);
|
||||
footer[1]=(crc>>8);
|
||||
footer[2]=(crc&0x8000)?0:0xff; //need one last level transition at end
|
||||
mipiSendMultiple(datas, lengths, 3);
|
||||
}
|
||||
|
||||
void mipiDsiSendShort(int type, uint8_t *data, int len) {
|
||||
DsiSPHdr *p=alloca(sizeof(DsiSPHdr)+2+len);
|
||||
p->sot=0xB8;
|
||||
p->datatype=type;
|
||||
memcpy(p->data, data, len);
|
||||
p->data[len]=calc_ecc((uint8_t*)&p->datatype);
|
||||
p->data[len+1]=(p->data[len]&0x80)?0:0xff; //need one last level transition at end
|
||||
mipiSend((uint8_t*)p, sizeof(DsiSPHdr)+2+len);
|
||||
}
|
2
components/mipidisp/mipi_dsi.h
Normal file
2
components/mipidisp/mipi_dsi.h
Normal file
@ -0,0 +1,2 @@
|
||||
void mipiDsiSendLong(int type, uint8_t *data, int len);
|
||||
void mipiDsiSendShort(int type, uint8_t *data, int len);
|
105
components/tme-esp32/adns9500.c
Normal file
105
components/tme-esp32/adns9500.c
Normal file
@ -0,0 +1,105 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "freertos/FreeRTOS.h"
|
||||
#include "freertos/task.h"
|
||||
#include "esp_system.h"
|
||||
#include "driver/spi_master.h"
|
||||
#include "soc/gpio_struct.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "esp_heap_alloc_caps.h"
|
||||
|
||||
#define ADNS_MOSI 19
|
||||
#define ADNS_MISO 21
|
||||
#define ADNS_CLK 23
|
||||
#define ADNS_CS 22
|
||||
|
||||
//#define DELAY() asm("nop; nop; nop; nop;nop; nop; nop; nop;nop; nop; nop; nop;nop; nop; nop; nop;")
|
||||
#define DELAY() ets_delay_us(10);
|
||||
|
||||
static void adnsWrite(int adr, int val) {
|
||||
int data=((adr|0x80)<<8)|val;
|
||||
gpio_set_level(ADNS_CS, 0);
|
||||
DELAY();
|
||||
for (int mask=0x8000; mask!=0; mask>>=1) {
|
||||
gpio_set_level(ADNS_MOSI, (data&mask)?1:0);
|
||||
gpio_set_level(ADNS_CLK, 0);
|
||||
DELAY();
|
||||
gpio_set_level(ADNS_CLK, 1);
|
||||
DELAY();
|
||||
}
|
||||
gpio_set_level(ADNS_CS, 1);
|
||||
}
|
||||
|
||||
static int adnsRead(int adr) {
|
||||
int data=((adr&0x7F)<<8);
|
||||
int out=0;
|
||||
gpio_set_level(ADNS_CS, 0);
|
||||
DELAY();
|
||||
for (int mask=0x8000; mask!=0; mask>>=1) {
|
||||
gpio_set_level(ADNS_MOSI, (data&mask)?1:0);
|
||||
gpio_set_level(ADNS_CLK, 0);
|
||||
DELAY();
|
||||
gpio_set_level(ADNS_CLK, 1);
|
||||
if (gpio_get_level(ADNS_MISO)) out|=mask;
|
||||
DELAY();
|
||||
}
|
||||
gpio_set_level(ADNS_CS, 1);
|
||||
return out&0xff;
|
||||
}
|
||||
|
||||
int adns9500_init() {
|
||||
volatile int delay;
|
||||
int t;
|
||||
gpio_config_t gpioconf[2]={
|
||||
{
|
||||
.pin_bit_mask=(1<<ADNS_MOSI)|(1<<ADNS_CS)|(1<<ADNS_CLK),
|
||||
.mode=GPIO_MODE_OUTPUT,
|
||||
.pull_up_en=GPIO_PULLUP_DISABLE,
|
||||
.pull_down_en=GPIO_PULLDOWN_DISABLE,
|
||||
.intr_type=GPIO_PIN_INTR_DISABLE
|
||||
},{
|
||||
.pin_bit_mask=(1<<ADNS_MISO),
|
||||
.mode=GPIO_MODE_INPUT,
|
||||
.pull_up_en=GPIO_PULLUP_ENABLE,
|
||||
.pull_down_en=GPIO_PULLDOWN_DISABLE,
|
||||
.intr_type=GPIO_PIN_INTR_DISABLE
|
||||
}
|
||||
};
|
||||
gpio_config(&gpioconf[0]);
|
||||
gpio_config(&gpioconf[1]);
|
||||
|
||||
int tout=5;
|
||||
int r;
|
||||
do {
|
||||
adnsWrite(0,0);
|
||||
adnsWrite(0x3A,0x5a); //Power-Up Reset
|
||||
vTaskDelay(50/portTICK_RATE_MS);
|
||||
adnsRead(0x2);
|
||||
adnsRead(0x3);
|
||||
adnsRead(0x4);
|
||||
adnsRead(0x5);
|
||||
adnsRead(0x6);
|
||||
|
||||
r=adnsRead(0);
|
||||
printf("ADNS: Read %X\n", r);
|
||||
tout--;
|
||||
} while (r!=0x33 && tout!=0);
|
||||
if (tout==0) return 0;
|
||||
|
||||
adnsWrite(0x20, 0); //Main laser turn on !!!
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
void adns900_get_dxdybtn(int *x, int *y, int *btn) {
|
||||
int16_t sx, sy;
|
||||
sx=adnsRead(0x3);
|
||||
sx|=adnsRead(0x4)<<8;
|
||||
sy=adnsRead(0x5);
|
||||
sy|=adnsRead(0x6)<<8;
|
||||
// printf("Mouse: %d %d\n", sx, sy);
|
||||
*x=sx;
|
||||
*y=sy;
|
||||
*btn=gpio_get_level(ADNS_MISO)?0:1;
|
||||
}
|
3
components/tme-esp32/adns9500.h
Normal file
3
components/tme-esp32/adns9500.h
Normal file
@ -0,0 +1,3 @@
|
||||
int adns9500_init();
|
||||
void adns900_get_dxdybtn(int *x, int *y, int *btn);
|
||||
|
@ -21,9 +21,6 @@
|
||||
#include "emu.h"
|
||||
#include "tmeconfig.h"
|
||||
|
||||
#include "mpu6050.h"
|
||||
#include "mpumouse.h"
|
||||
|
||||
unsigned char *romdata;
|
||||
|
||||
void emuTask(void *pvParameters)
|
||||
@ -36,17 +33,6 @@ void emuTask(void *pvParameters)
|
||||
tmeStartEmu(ram, romdata);
|
||||
}
|
||||
|
||||
void mouseTask(void *pvParameters)
|
||||
{
|
||||
printf("Starting mouse task...\n");
|
||||
while(!mpu6050_init()) {
|
||||
printf("Can't init MPU....\n");
|
||||
vTaskDelay(100);
|
||||
}
|
||||
|
||||
mpuMouseEmu();
|
||||
}
|
||||
|
||||
|
||||
void app_main()
|
||||
{
|
||||
@ -60,7 +46,6 @@ void app_main()
|
||||
err=esp_partition_mmap(part, 0, 128*1024, SPI_FLASH_MMAP_DATA, (const void**)&romdata, &hrom);
|
||||
if (err!=ESP_OK) printf("Couldn't map bootrom part!\n");
|
||||
printf("Starting emu...\n");
|
||||
// xTaskCreatePinnedToCore(&mouseTask, "mouse", 6*1024, NULL, 6, NULL, 0);
|
||||
xTaskCreatePinnedToCore(&emuTask, "emu", 8*1024, NULL, 5, NULL, 0);
|
||||
xTaskCreatePinnedToCore(&emuTask, "emu", 6*1024, NULL, 5, NULL, 0);
|
||||
}
|
||||
|
||||
|
@ -16,9 +16,8 @@
|
||||
#include "soc/gpio_struct.h"
|
||||
#include "driver/gpio.h"
|
||||
#include "esp_heap_alloc_caps.h"
|
||||
#include "mpumouse.h"
|
||||
#include "mouse.h"
|
||||
|
||||
#include "adns9500.h"
|
||||
|
||||
#include "mipi.h"
|
||||
#include "mipi_dsi.h"
|
||||
@ -31,92 +30,7 @@ typedef struct {
|
||||
} DispPacket;
|
||||
|
||||
//Copied from the X163QLN01 appliation note.
|
||||
DispPacket initPackets[]={
|
||||
#if 0
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x39, 0xBD, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBE, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBF, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBB, 3, {0x07, 0x07, 0x07}},
|
||||
{0x39, 0xD0, 1, {0x00}},
|
||||
{0x39, 0xD1, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xD2, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xD3, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xC7, 1, {0x40}},
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x15, 0xEB, 1, {0x02}},
|
||||
{0x15, 0xF5, 1, {0x10}},
|
||||
{0x39, 0xED, 8, {0x48, 0x48, 0x48, 0x48, 0x48, 0x48, 0x48, 0x48}},
|
||||
{0x39, 0xC7, 8, {0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F}},
|
||||
{0x39, 0xFE, 2, {0x08, 0x08}},
|
||||
{0x39, 0xC3, 3, {0xF2, 0xF2, 0xF2}},
|
||||
{0x39, 0xE9, 3, {0x00, 0x00, 0x00}},
|
||||
{0x15, 0xCA, 1, {0x04}},
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x39, 0xB0, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xB1, 3, {0x05, 0x05, 0x05}},
|
||||
{0x39, 0xB2, 3, {0x01, 0x01, 0x01}},
|
||||
{0x39, 0xB4, 3, {0x07, 0x07, 0x07}},
|
||||
{0x39, 0xB5, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xB6, 3, {0x55, 0x55, 0x55}},
|
||||
{0x39, 0xB7, 3, {0x35, 0x35, 0x35}},
|
||||
{0x39, 0xB8, 3, {0x23, 0x23, 0x23}},
|
||||
{0x39, 0xB9, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xBA, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xBE, 3, {0x32, 0x32, 0x32}},
|
||||
{0x39, 0xC2, 12, {0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B}},
|
||||
{0x39, 0xCF, 7, {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}},
|
||||
{0x15, 0x35, 1, {0x00}},
|
||||
{0x15, 0x36, 1, {0x00}},
|
||||
{0x15, 0xC0, 1, {0x28}},
|
||||
{0x32, 0x00, 1, {0x00}},
|
||||
{0x15, 0x51, 1, {0x00}},
|
||||
{0x05, 0x11, 1, {0x00}},
|
||||
{0x05, 0x29, 1, {0x00}},
|
||||
#endif
|
||||
#if 0
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x39, 0xBD, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBE, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBF, 5, {0x01, 0x01, 0x01, 0x01, 0x01}},
|
||||
{0x39, 0xBB, 3, {0x07, 0x07, 0x07}},
|
||||
{0x39, 0xD0, 1, {0x00}},
|
||||
{0x39, 0xD1, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xD2, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xD3, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xC7, 1, {0x40}},
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x15, 0xEB, 1, {0x02}},
|
||||
{0x15, 0xF5, 1, {0x10}},
|
||||
{0x39, 0xED, 8, {0x48, 0x48, 0x48, 0x48, 0x48, 0x48, 0x48, 0x48}},
|
||||
{0x39, 0xC7, 8, {0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F, 0x0F}},
|
||||
{0x39, 0xFE, 2, {0x08, 0x08}},
|
||||
{0x39, 0xC3, 3, {0xF2, 0xF2, 0xF2}},
|
||||
{0x39, 0xE9, 3, {0x00, 0x00, 0x00}},
|
||||
{0x15, 0xCA, 1, {0x04}},
|
||||
{0x39, 0xF0, 5, {0x55, 0x55, 0x55, 0x55, 0x55}},
|
||||
{0x39, 0xB0, 3, {0x00, 0x00, 0x00}},
|
||||
{0x39, 0xB1, 3, {0x05, 0x05, 0x05}},
|
||||
{0x39, 0xB2, 3, {0x01, 0x01, 0x01}},
|
||||
{0x39, 0xB4, 3, {0x07, 0x07, 0x07}},
|
||||
{0x39, 0xB5, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xB6, 3, {0x55, 0x55, 0x55}},
|
||||
{0x39, 0xB7, 3, {0x35, 0x35, 0x35}},
|
||||
{0x39, 0xB8, 3, {0x23, 0x23, 0x23}},
|
||||
{0x39, 0xB9, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xBA, 3, {0x03, 0x03, 0x03}},
|
||||
{0x39, 0xBE, 3, {0x32, 0x32, 0x32}},
|
||||
{0x39, 0xC2, 12, {0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B, 0x0B}},
|
||||
{0x39, 0xCF, 7, {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}},
|
||||
{0x15, 0x35, 1, {0x00}},
|
||||
{0x15, 0x36, 1, {0x00}},
|
||||
{0x15, 0xC0, 1, {0x28}},
|
||||
{0x32, 0x00, 1, {0x00}},
|
||||
{0x15, 0x51, 1, {0x00}},
|
||||
{0x05, 0x11, 1, {0x00}},
|
||||
{0x05, 0x29, 1, {0x00}},
|
||||
#endif
|
||||
#if 1
|
||||
const DispPacket initPackets[]={
|
||||
{0x39, 0xF0, 5, {0x55, 0xAA, 0x52, 0x08, 0x00}},
|
||||
{0x39, 0xBD, 5, {0x01, 0x90, 0x14, 0x14, 0x00}},
|
||||
{0x39, 0xBE, 5, {0x01, 0x90, 0x14, 0x14, 0x01}},
|
||||
@ -147,7 +61,6 @@ DispPacket initPackets[]={
|
||||
{0x32, 0, 0, {0}},
|
||||
{0x05, 0x11, 1, {0x00}}, //exit_sleep_mode
|
||||
{0x05, 0x29, 1, {0x00}}, //turn display on
|
||||
#endif
|
||||
{0x15, 0x3A, 1, {0x55}}, //16-bit mode
|
||||
// {0x29, 0x2B, 4, {0x00, 0x00, 0x00, 0xEF}},
|
||||
{0,0,0,{0}}
|
||||
@ -223,10 +136,12 @@ SemaphoreHandle_t dispSem = NULL;
|
||||
|
||||
#define LINESPERBUF 1
|
||||
|
||||
void IRAM_ATTR displayTask(void *arg) {
|
||||
|
||||
static void initLcd() {
|
||||
mipiInit();
|
||||
vTaskDelay(20/portTICK_RATE_MS); //give screen a sec
|
||||
for (int j=0; j<2; j++) { //Init multiple times; for mysterious reasons it sometimes doesn't catch first time.
|
||||
for (int i=0; initPackets[i].type!=0; i++) {
|
||||
mipiResync();
|
||||
if (initPackets[i].type==0x39 || initPackets[i].type==0x29) {
|
||||
uint8_t data[17];
|
||||
data[0]=initPackets[i].addr;
|
||||
@ -238,11 +153,15 @@ void IRAM_ATTR displayTask(void *arg) {
|
||||
if (initPackets[i].type==5) vTaskDelay(300/portTICK_RATE_MS);
|
||||
}
|
||||
}
|
||||
|
||||
printf("Inited.\n");
|
||||
}
|
||||
printf("Display inited.\n");
|
||||
}
|
||||
|
||||
void IRAM_ATTR displayTask(void *arg) {
|
||||
uint8_t *img=malloc((LINESPERBUF*320*2)+1);
|
||||
assert(img);
|
||||
|
||||
|
||||
while(1) {
|
||||
int l=0;
|
||||
mipiResync();
|
||||
@ -258,10 +177,10 @@ void IRAM_ATTR displayTask(void *arg) {
|
||||
}
|
||||
l++;
|
||||
if (l>=LINESPERBUF || j==319) {
|
||||
//mipiDsiSendLong(0x39, img, (LINESPERBUF*320*2)+1);
|
||||
mipiDsiSendLong(0x39, img, (LINESPERBUF*320*2)+1);
|
||||
img[0]=0x3c;
|
||||
l=0;
|
||||
*p=&img[1];
|
||||
p=&img[1];
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -273,13 +192,17 @@ void dispDraw(uint8_t *mem) {
|
||||
int dx, dy, btn;
|
||||
currFbPtr=mem;
|
||||
xSemaphoreGive(dispSem);
|
||||
// mpuMouseGetDxDyBtn(&dx, &dy, &btn);
|
||||
// mouseMove(dx, dy, btn);
|
||||
adns900_get_dxdybtn(&dx, &dy, &btn);
|
||||
mouseMove(dx, dy, btn);
|
||||
}
|
||||
|
||||
|
||||
void dispInit() {
|
||||
initLcd();
|
||||
printf("spi_lcd_init()\n");
|
||||
int ret=adns9500_init();
|
||||
if (!ret) printf("No mouse found!\n");
|
||||
|
||||
dispSem=xSemaphoreCreateBinary();
|
||||
#if CONFIG_FREERTOS_UNICORE
|
||||
xTaskCreatePinnedToCore(&displayTask, "display", 3000, NULL, 5, NULL, 0);
|
||||
|
@ -90,7 +90,7 @@ void m68k_write_memory_8(unsigned int address, unsigned int value) {
|
||||
ncrWrite((address>>4)&0x7, (address>>9)&1, value);
|
||||
} else if (address >= 0x800000 && address < 0xC00000) {
|
||||
sccWrite(address, value);
|
||||
printf("PC %x: Write to %x: %x\n", pc, address, value);
|
||||
// printf("PC %x: Write to %x: %x\n", pc, address, value);
|
||||
} else {
|
||||
printf("PC %x: Write to %x: %x\n", pc, address, value);
|
||||
}
|
||||
|
@ -43,7 +43,7 @@ static Scc scc;
|
||||
static void raiseInt(int chan) {
|
||||
if ((scc.wr1[chan]&1) && (scc.intpending&(~scc.intpendingOld))) {
|
||||
scc.intpendingOld=scc.intpending;
|
||||
printf("SCC int, pending %x\n", scc.intpending);
|
||||
// printf("SCC int, pending %x\n", scc.intpending);
|
||||
sccIrq(1);
|
||||
}
|
||||
}
|
||||
@ -127,7 +127,7 @@ unsigned int sccRead(unsigned int addr) {
|
||||
} else if (reg==15) {
|
||||
val=scc.wr15[chan];
|
||||
}
|
||||
printf("SCC: read from chan %d reg %d val %x\n", chan, reg, val);
|
||||
// printf("SCC: read from chan %d reg %d val %x\n", chan, reg, val);
|
||||
return val;
|
||||
}
|
||||
|
||||
|
@ -81,8 +81,8 @@ CONFIG_PARTITION_TABLE_CUSTOM_FILENAME="partitions.csv"
|
||||
CONFIG_PARTITION_TABLE_CUSTOM_APP_BIN_OFFSET=0x10000
|
||||
CONFIG_PARTITION_TABLE_FILENAME="partitions.csv"
|
||||
CONFIG_APP_OFFSET=0x10000
|
||||
CONFIG_OPTIMIZATION_LEVEL_DEBUG=y
|
||||
# CONFIG_OPTIMIZATION_LEVEL_RELEASE is not set
|
||||
# CONFIG_OPTIMIZATION_LEVEL_DEBUG is not set
|
||||
CONFIG_OPTIMIZATION_LEVEL_RELEASE=y
|
||||
|
||||
#
|
||||
# Component config
|
||||
@ -180,7 +180,7 @@ CONFIG_FATFS_MAX_LFN=255
|
||||
#
|
||||
# FreeRTOS
|
||||
#
|
||||
CONFIG_FREERTOS_UNICORE=y
|
||||
# CONFIG_FREERTOS_UNICORE is not set
|
||||
CONFIG_FREERTOS_CORETIMER_0=y
|
||||
# CONFIG_FREERTOS_CORETIMER_1 is not set
|
||||
CONFIG_FREERTOS_HZ=100
|
||||
|
Loading…
Reference in New Issue
Block a user