Nikolai Trushnikov / FT813

Dependents:   Chromatograph_Mobile

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers FT_GPU_Hal.cpp Source File

FT_GPU_Hal.cpp

00001 /* mbed Library for FTDI FT813  Enbedded Video Engine "EVE"
00002  * based on Original Code Sample from FTDI
00003  * ported to mbed by Peter Drescher, DC2PD 2014
00004  * Released under the MIT License: http://mbed.org/license/mit 
00005  * 19.09.14 changed to shorter function names  
00006  * FTDI was using very long names. 
00007  * Ft_App_Flush_Co_Buffer -> Flush_Co_Buffer ...  */
00008 
00009 #include "FT_Platform.h"
00010 #include "mbed.h"
00011 #include "FT_LCD_Type.h"
00012 //Serial pc(USBTX, USBRX);
00013 //Serial pc(SERIAL_TX,SERIAL_RX,115200);
00014 #define SPI_SPEED_START 10000000
00015 #define SPI_SPEED_AFTER 27000000
00016 
00017 FT813::FT813(PinName mosi,
00018             PinName miso,
00019             PinName sck,
00020             PinName ss,
00021             PinName intr,
00022             PinName pd)
00023 :
00024 _spi(mosi, miso, sck),
00025 _ss(ss),
00026 _pd(pd),
00027 _f800_isr(InterruptIn(intr))
00028 {
00029     _spi.format(8, 0);                  // 8 bit spi mode 0
00030     _spi.frequency(SPI_SPEED_START);          // start with 10 Mhz SPI clock
00031     _ss = 1;                           // cs high
00032     _pd = 1;                           // PD high
00033     _IsOn=Bootup();
00034     _address = 0;
00035     _bitmap_count = 0;
00036     _bitmapCount = 0;
00037     _bitmapAddress = 0;
00038 }
00039 
00040 
00041 ft_bool_t FT813::Bootup(void)
00042 {
00043    //printf("Bootup() entered\r\n");//temp
00044     Open();
00045 
00046     return BootupConfig();   
00047 }
00048 
00049 ft_bool_t FT813::IsOn(void)
00050 {
00051     return FT813::_IsOn;
00052 }
00053 
00054 char FT813::BootupConfig(void)
00055 {
00056     ft_uint8_t chipid;
00057     /* Do a power cycle for safer side */
00058     Powercycle(FT_TRUE);
00059     /*
00060     7/8/16: Curt added the sleep delay below...
00061     */
00062 //  Sleep(30);
00063     
00064     /* Set the clk to external clock */
00065     HostCommand(FT_GPU_INTERNAL_OSC);
00066     Sleep(10);
00067     
00068     /* Access address 0 to wake up the FT813 */
00069     HostCommand(FT_GPU_ACTIVE_M);
00070     Sleep(500);
00071 
00072     /* Switch PLL output to 48MHz */
00073     HostCommand(FT_GPU_PLL_48M);
00074     Sleep(10);
00075 
00076     /* Do a core reset for safer side */
00077     HostCommand(FT_GPU_CORE_RESET);
00078     Sleep(500);
00079     //Read Register ID to check if FT813 is ready.
00080     chipid = Rd8(REG_ID);
00081   //chipid = Rd8(0x0C0000);
00082     //pc.printf("ID1: 0x%08X\n", chipid);//temp
00083     
00084     //Если дисплей не отвечает то прервать инициализацию
00085     char sec=0;
00086     while(chipid != 0x7C) //раскомментить как заработает    
00087     {
00088         wait_ms(100);
00089         sec++;
00090         if (sec>3)
00091             {
00092             printf("ERR!: Display is not connected\r\n");
00093             return 0;
00094             } 
00095         }
00096     //tmp
00097     //printf("ID2: 0x%08X\n", chipid);//tmp
00098 
00099     // Speed up
00100 //    _spi.frequency(50000000);           // 30 Mhz SPI clock DC
00101     _spi.frequency(SPI_SPEED_AFTER);           // 20 Mhz SPI clock DC
00102 //    _spi.frequency(12000000);           // 12 Mhz SPI clock
00103     /* Configuration of LCD display */
00104     DispHCycle = my_DispHCycle;
00105     Wr16(REG_HCYCLE, DispHCycle);
00106     DispHOffset = my_DispHOffset;
00107     Wr16(REG_HOFFSET, DispHOffset);
00108     DispWidth = my_DispWidth;
00109     Wr16(REG_HSIZE, DispWidth);
00110     DispHSync0 = my_DispHSync0;
00111     Wr16(REG_HSYNC0, DispHSync0);
00112     DispHSync1 = my_DispHSync1;
00113     Wr16(REG_HSYNC1, DispHSync1);
00114     DispVCycle = my_DispVCycle;
00115     Wr16(REG_VCYCLE, DispVCycle);
00116     DispVOffset = my_DispVOffset;
00117     Wr16(REG_VOFFSET, DispVOffset);
00118     DispHeight = my_DispHeight;
00119     Wr16(REG_VSIZE, DispHeight);
00120     DispVSync0 = my_DispVSync0;
00121     Wr16(REG_VSYNC0, DispVSync0);
00122     DispVSync1 = my_DispVSync1;
00123     Wr16(REG_VSYNC1, DispVSync1);
00124     DispSwizzle = my_DispSwizzle;
00125     Wr8(REG_SWIZZLE, DispSwizzle);
00126     DispPCLKPol = my_DispPCLKPol;
00127     Wr8(REG_PCLK_POL, DispPCLKPol);
00128     Wr8(REG_CSPREAD, 1); //поменяно для Riverdi 0 на 1
00129     DispPCLK = my_DispPCLK;
00130     Wr8(REG_PCLK, DispPCLK);    // After this display is visible on the LCD
00131 
00132     Wr16(REG_PWM_HZ, 10000);
00133 //#ifdef Inv_Backlite               // turn on backlite
00134 //    Wr16(REG_PWM_DUTY, 0);
00135 //#else
00136     Wr16(REG_PWM_DUTY, 255); // Brightness 127
00137 //#endif
00138     Wr8(REG_GPIO_DIR, 0x82);  //| Rd8(REG_GPIO_DIR));
00139     Wr8(REG_GPIO, 0x080);     //| Rd8(REG_GPIO));
00140 
00141     Wr32(RAM_DL, CLEAR(1, 1, 1));
00142     Wr32(RAM_DL+4, DISPLAY());
00143     Wr32(REG_DLSWAP, 1);
00144 
00145     Wr16(REG_PCLK, DispPCLK);
00146 
00147     /* Touch configuration - configure the resistance value to 1200 */
00148     /* This value is specific to customer requirement and derived by experiment */
00149 //    Wr16(REG_TOUCH_RZTHRESH,2400);
00150     Wr16(REG_TOUCH_RZTHRESH, 1800); //поменяно с 0xFFFF на 1800
00151     return 1; //дисплей включен и настроен
00152 }
00153 
00154 /* API to initialize the SPI interface */
00155 ft_bool_t FT813::Init()
00156 {
00157     // This is done in the constructor
00158     return 1;
00159 }
00160 
00161 ft_bool_t FT813::Open()
00162 {
00163     cmd_fifo_wp = dl_buff_wp = 0;
00164     status = OPENED;
00165     return 1;
00166 }
00167 
00168 ft_void_t FT813::Close()
00169 {
00170     status = CLOSED;
00171 }
00172 
00173 ft_void_t FT813::DeInit()
00174 {
00175 }
00176 
00177 /*The APIs for reading/writing transfer continuously only with small buffer system*/
00178 ft_void_t FT813::StartTransfer(FT_GPU_TRANSFERDIR_T rw, ft_uint32_t addr)
00179 {
00180     if (FT_GPU_READ == rw) {
00181         _ss = 0;       // cs low
00182         _spi.write(addr >> 16);
00183         _spi.write(addr >> 8);
00184         _spi.write(addr & 0xff);
00185         _spi.write(0); //Dummy Read Byte
00186         status = READING;
00187     } else {
00188         _ss = 0;       // cs low
00189         _spi.write(0x80 | (addr >> 16));
00190         _spi.write(addr >> 8);
00191         _spi.write(addr & 0xff);
00192         status = WRITING;
00193     }
00194 }
00195 
00196 
00197 /*The APIs for writing transfer continuously only*/
00198 ft_void_t FT813::StartCmdTransfer(FT_GPU_TRANSFERDIR_T rw, ft_uint16_t count)
00199 {
00200     StartTransfer(rw, cmd_fifo_wp + RAM_CMD);
00201 }
00202 
00203 ft_uint8_t FT813::TransferString(const ft_char8_t *string)
00204 {
00205     ft_uint16_t length = strlen(string);
00206     while(length --) {
00207        Transfer8(*string);
00208        string++;
00209     }
00210     //Append one null as ending flag
00211     Transfer8(0);
00212     return(1);
00213 }
00214 
00215 
00216 ft_uint8_t FT813::Transfer8(ft_uint8_t value)
00217 {
00218         return _spi.write(value);
00219 }
00220 
00221 
00222 ft_uint16_t FT813::Transfer16(ft_uint16_t value)
00223 {
00224     ft_uint16_t retVal = 0;
00225 
00226         if (status == WRITING) {
00227         Transfer8(value & 0xFF);//LSB first
00228         Transfer8((value >> 8) & 0xFF);
00229     } else {
00230         retVal = Transfer8(0);
00231         retVal |= (ft_uint16_t)Transfer8(0) << 8;
00232     }
00233 
00234     return retVal;
00235 }
00236 
00237 ft_uint32_t FT813::Transfer32(ft_uint32_t value)
00238 {
00239     ft_uint32_t retVal = 0;
00240     if (status == WRITING) {
00241         Transfer16(value & 0xFFFF);//LSB first
00242         Transfer16((value >> 16) & 0xFFFF);
00243     } else {
00244         retVal = Transfer16(0);
00245         retVal |= (ft_uint32_t)Transfer16(0) << 16;
00246     }
00247     return retVal;
00248 }
00249 
00250 ft_void_t FT813::EndTransfer()
00251 {
00252     _ss = 1;
00253     status = OPENED;
00254 }
00255 
00256 ft_uint8_t FT813::Rd8(ft_uint32_t addr)
00257 {
00258     ft_uint8_t value;
00259     StartTransfer(FT_GPU_READ, addr);
00260     value = Transfer8(0);
00261     EndTransfer();
00262     return value;
00263 }
00264 
00265 ft_uint16_t FT813::Rd16(ft_uint32_t addr)
00266 {
00267     ft_uint16_t value;
00268     StartTransfer(FT_GPU_READ, addr);
00269     value = Transfer16(0);
00270     EndTransfer();
00271     return value;
00272 }
00273 
00274 ft_uint32_t FT813::Rd32(ft_uint32_t addr)
00275 {
00276     ft_uint32_t value;
00277     StartTransfer(FT_GPU_READ, addr);
00278     value = Transfer32(0);
00279     EndTransfer();
00280     return value;
00281 }
00282 
00283 ft_void_t FT813::Wr8(ft_uint32_t addr, ft_uint8_t v)
00284 {
00285 //    StartTransfer(FT_GPU_WRITE, addr);
00286 //    if (FT_GPU_READ == rw) {  // if (FT_GPU_READ == FT_GPU_WRITE)
00287 //        _ss = 0;       // cs low
00288 //        _spi.write(addr >> 16);
00289 //        _spi.write(addr >> 8);
00290 //        _spi.write(addr & 0xff);
00291 //        _spi.write(0); //Dummy Read Byte
00292 //        status = READING;
00293 //    } else {
00294         _ss = 0;       // cs low
00295         _spi.write(0x80 | (addr >> 16));
00296         _spi.write(addr >> 8);
00297         _spi.write(addr & 0xff);
00298         status = WRITING;
00299 //    }
00300 
00301 //    Transfer8(v);
00302     _spi.write(v);
00303 //    EndTransfer();
00304     _ss = 1;
00305     status = OPENED;
00306 }
00307 
00308 ft_void_t FT813::Wr16(ft_uint32_t addr, ft_uint16_t v)
00309 {
00310     StartTransfer(FT_GPU_WRITE, addr);
00311     Transfer16(v);
00312     EndTransfer();
00313 }
00314 
00315 ft_void_t FT813::Wr32(ft_uint32_t addr, ft_uint32_t v)
00316 {
00317     StartTransfer(FT_GPU_WRITE, addr);
00318     Transfer32(v);
00319     EndTransfer();
00320 }
00321 
00322 ft_void_t FT813::HostCommand(ft_uint8_t cmd)
00323 {
00324   _ss = 0;
00325   _spi.write(cmd);
00326   _spi.write(0);
00327   _spi.write(0);
00328   _ss = 1;
00329 }
00330 
00331 ft_void_t FT813::ClockSelect(FT_GPU_PLL_SOURCE_T pllsource)
00332 {
00333    HostCommand(pllsource);
00334 }
00335 
00336 ft_void_t FT813::PLL_FreqSelect(FT_GPU_PLL_FREQ_T freq)
00337 {
00338    HostCommand(freq);
00339 }
00340 
00341 ft_void_t FT813::PowerModeSwitch(FT_GPU_POWER_MODE_T pwrmode)
00342 {
00343    HostCommand(pwrmode);
00344 }
00345 
00346 ft_void_t FT813::CoreReset()
00347 {
00348    HostCommand(0x68);
00349 }
00350 
00351 ft_void_t FT813::Updatecmdfifo(ft_uint16_t count)
00352 {
00353      cmd_fifo_wp  = (cmd_fifo_wp + count) & 4095;
00354     //4 byte alignment
00355      cmd_fifo_wp = (cmd_fifo_wp + 3) & 0xffc;
00356     Wr16(REG_CMD_WRITE, cmd_fifo_wp);
00357 }
00358 
00359 ft_uint16_t FT813::fifo_Freespace()
00360 {
00361     ft_uint16_t fullness,retval;
00362 
00363     fullness = (cmd_fifo_wp - Rd16(REG_CMD_READ)) & 4095;
00364     retval = (FT_CMD_FIFO_SIZE - 4) - fullness;
00365     return (retval);
00366 }
00367 
00368 ft_void_t FT813::WrCmdBuf(ft_uint8_t *buffer, ft_uint16_t count)
00369 {
00370     ft_uint32_t length =0, SizeTransfered = 0;
00371 
00372 #define MAX_CMD_FIFO_TRANSFER   fifo_Freespace()
00373     do {
00374         length = count;
00375         if (length > MAX_CMD_FIFO_TRANSFER) {
00376             length = MAX_CMD_FIFO_TRANSFER;
00377         }
00378         CheckCmdBuffer(length);
00379 
00380         StartCmdTransfer(FT_GPU_WRITE, length);
00381 
00382         SizeTransfered = 0;
00383         while (length--) {
00384 //            Transfer8(*buffer);
00385             _spi.write(*buffer);
00386             buffer++;
00387             SizeTransfered++;
00388         }
00389         length = SizeTransfered;
00390 
00391         EndTransfer();
00392         Updatecmdfifo(length);
00393 
00394         WaitCmdfifo_empty();
00395 
00396         count -= length;
00397     } while (count > 0);
00398 }
00399 
00400 ft_void_t FT813::WrCmdBufFromFlash(FT_PROGMEM ft_prog_uchar8_t *buffer, ft_uint16_t count)
00401 {
00402     ft_uint32_t length =0, SizeTransfered = 0;
00403 
00404 #define MAX_CMD_FIFO_TRANSFER   fifo_Freespace()
00405     do {
00406         length = count;
00407         if (length > MAX_CMD_FIFO_TRANSFER) {
00408             length = MAX_CMD_FIFO_TRANSFER;
00409         }
00410         CheckCmdBuffer(length);
00411 
00412         StartCmdTransfer(FT_GPU_WRITE,length);
00413 
00414         SizeTransfered = 0;
00415         while (length--) {
00416             Transfer8(ft_pgm_read_byte_near(buffer));
00417             buffer++;
00418             SizeTransfered++;
00419         }
00420         length = SizeTransfered;
00421 
00422         EndTransfer();
00423         Updatecmdfifo(length);
00424 
00425         WaitCmdfifo_empty();
00426 
00427         count -= length;
00428     } while (count > 0);
00429 }
00430 
00431 ft_void_t FT813::CheckCmdBuffer(ft_uint16_t count)
00432 {
00433    ft_uint16_t getfreespace;
00434    do {
00435         getfreespace = fifo_Freespace();
00436    } while(getfreespace < count);
00437 }
00438 
00439 ft_void_t FT813::WaitCmdfifo_empty()
00440 {
00441    while(Rd16(REG_CMD_READ) != Rd16(REG_CMD_WRITE));
00442 
00443     cmd_fifo_wp = Rd16(REG_CMD_WRITE);
00444 }
00445 
00446 ft_void_t FT813::WaitLogo_Finish()
00447 {
00448     ft_int16_t cmdrdptr, cmdwrptr;
00449 
00450     do {
00451          cmdrdptr = Rd16(REG_CMD_READ);
00452          cmdwrptr = Rd16(REG_CMD_WRITE);
00453     } while ((cmdwrptr != cmdrdptr) || (cmdrdptr != 0));
00454     cmd_fifo_wp = 0;
00455 }
00456 
00457 ft_void_t FT813::ResetCmdFifo()
00458 {
00459     cmd_fifo_wp = 0;
00460 }
00461 
00462 ft_void_t FT813::WrCmd32(ft_uint32_t cmd)
00463 {
00464      CheckCmdBuffer(sizeof(cmd));
00465 
00466      Wr32(RAM_CMD + cmd_fifo_wp, cmd);
00467 
00468      Updatecmdfifo(sizeof(cmd));
00469 }
00470 
00471 ft_void_t FT813::ResetDLBuffer()
00472 {
00473     dl_buff_wp = 0;
00474 }
00475 
00476 /* Toggle PD_N pin of FT813 board for a power cycle*/
00477 ft_void_t FT813::Powercycle(ft_bool_t up)
00478 {
00479     if (up)
00480     {
00481         //Toggle PD_N from low to high for power up switch
00482         _pd = 0;
00483         Sleep(20);
00484 
00485         _pd = 1;
00486         Sleep(20);
00487     } else {
00488         //Toggle PD_N from high to low for power down switch
00489         _pd = 1;
00490         Sleep(20);
00491 
00492         _pd = 0;
00493         Sleep(20);
00494     }
00495 }
00496 
00497 ft_void_t FT813::WrMemFromFlash(ft_uint32_t addr, const ft_prog_uchar8_t *buffer, ft_uint32_t length)
00498 {
00499     //ft_uint32_t SizeTransfered = 0;
00500 
00501     StartTransfer(FT_GPU_WRITE,addr);
00502 
00503     while (length--) {
00504         Transfer8(ft_pgm_read_byte_near(buffer));
00505         buffer++;
00506     }
00507 
00508     EndTransfer();
00509 }
00510 
00511 ft_void_t FT813::WrMem(ft_uint32_t addr, const ft_uint8_t *buffer, ft_uint32_t length)
00512 {
00513     //ft_uint32_t SizeTransfered = 0;
00514 
00515     StartTransfer(FT_GPU_WRITE,addr);
00516 
00517     while (length--) {
00518         Transfer8(*buffer);
00519         buffer++;
00520     }
00521 
00522     EndTransfer();
00523 }
00524 
00525 ft_void_t FT813::RdMem(ft_uint32_t addr, ft_uint8_t *buffer, ft_uint32_t length)
00526 {
00527     //ft_uint32_t SizeTransfered = 0;
00528 
00529     StartTransfer(FT_GPU_READ,addr);
00530 
00531     while (length--) {
00532        *buffer = Transfer8(0);
00533        buffer++;
00534     }
00535 
00536     EndTransfer();
00537 }
00538 
00539 ft_int32_t FT813::Dec2Ascii(ft_char8_t *pSrc, ft_int32_t value)
00540 {
00541     ft_int16_t Length;
00542     ft_char8_t *pdst, charval;
00543     ft_int32_t CurrVal = value, tmpval,i;
00544     ft_char8_t tmparray[16], idx = 0;
00545 
00546     Length = strlen(pSrc);
00547     pdst = pSrc + Length;
00548 
00549     if(0 == value) {
00550         *pdst++ = '0';
00551         *pdst++ = '\0';
00552         return 0;
00553     }
00554 
00555     if(CurrVal < 0) {
00556         *pdst++ = '-';
00557         CurrVal = - CurrVal;
00558     }
00559     /* insert the value */
00560     while(CurrVal > 0) {
00561         tmpval = CurrVal;
00562         CurrVal /= 10;
00563         tmpval = tmpval - CurrVal*10;
00564         charval = '0' + tmpval;
00565         tmparray[idx++] = charval;
00566     }
00567 
00568     for(i = 0; i < idx; i++) {
00569         *pdst++ = tmparray[idx - i - 1];
00570     }
00571     *pdst++ = '\0';
00572 
00573     return 0;
00574 }
00575 
00576 ft_void_t FT813::Sleep(ft_uint16_t ms)
00577 {
00578     wait_ms(ms);
00579 }
00580 
00581 ft_void_t FT813::Sound_ON()
00582 {
00583      Wr8(REG_GPIO, 0x02 | Rd8(REG_GPIO));
00584 }
00585 
00586 ft_void_t FT813::Sound_OFF()
00587 {
00588      Wr8(REG_GPIO, 0xFD & Rd8(REG_GPIO));
00589 }