Kinetis Microcontrollers Knowledge Base

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Kinetis Microcontrollers Knowledge Base

Discussions

Sort by:
Introduction With the growth of the Internet of Things (IoT), more and more applications are incorporating the use of sensors while also requiring power efficiency and increased performance.  A popular interface for these sensors is the I2C protocol. The I2C bus is a great protocol that is a true multi-master protocol and allows for each bus to contain many devices.  As the performance demand of the application grows, so will the speed of the I2C bus as it will be necessary to get more data from the sensors and/or at a faster rate.  Many applications may already have a need to operate an I2C bus at 400 kHz or more.  Higher data rates means the MCU core will need to spend more time servicing the I2C transactions.  The DMA module is one good way to free up the core in order to let it tend to other aspects of the application.  This can add much needed or much desired performance to applications.  Especially applications that may be using small, power efficient, single core MCUs. It may seem like an easy, straight-forward task to add I2C reads from a sensor to an application.  However I2C is a time sensitive protocol and consequently, so is the I2C peripherals on MCUs.  It is important to understand the time requirements and how to overcome them. The recommended approach is to use DMA to transfer the received I2C data to the desired buffer in your application software.  This document is going to outline how to setup your DMA and provide an example of how to do this for a KW40 device using the Kinetis SDK version 1.3.  The KW40 is being targeted because this is a small, power efficient MCU that incorporates a radio for your wireless applications and as such, it is likely that your application could need this DMA approach.  The KSDK version 1.3 is being targeted because this version of the SDK does not currently support DMA transactions for the I2C peripheral. Understanding the Kinetis I2C peripheral module Before getting into the specifics of creating a DMA enabled I2C driver, it is important to understand some basics of the Kinetis I2C peripheral module.  This module handles a lot of the low-level timing.  However the I2C registers must be serviced in a timely manner to operate correctly.  Take the case of a master reading data from a typical I2C sensor as shown in the diagram below. In the diagram above, the red lines indicate points in the transaction where software or DMA needs to interact with the I2C peripheral to ensure the transaction happens correctly.  To begin a transaction the core must change the MST bit which puts a start bit on the bus (marked by symbol ST).  Immediately following this, the core should then also write the target slave's address (Device Address) including the read/write bit (R/W).  Once this transaction is complete, the I2C will issue an interrupt and then the core should write the register address to be read from. Upon completion of that being put on the bus, the I2C will issue another interrupt and the master should then put a repeated start (SR) on the bus as well as the slave's address again.  Now the slave will send data to the master (once the master begins the transaction by issuing a dummy read of the I2C data register).  In the standard configuration, the I2C peripheral will automatically send the NAK or AK depending on the configuration of the TXAK bit in the I2C peripheral.  Because of this automation, it is important that this bit be handled properly and is configured one frame in advance. Furthermore, to ensure that the NAK bit is sent at the appropriate time, the TXAK bit must be set when the second to last byte is received.  The timing of this configuration change is very important to ensuring that the transaction happens properly. This document will describe how to use DMA to receive the data.  The DMA will be configured before the transaction begins and will be used to receive the data from the slave.  The document will also discuss options to handle proper NAK'ing of the data to end the transaction. Writing a DMA I2C master receive function The first step in adding DMA capability to your SDK driver is to create a new receive function with an appropriate name.  For this example, the newly created receive function is named I2C_DRV_MasterReceiveDataDMA.  To create this function, the I2C_DRV_MasterReceive function (which is called for both blocking and non-blocking) was copied and then modified by removing the blocking capability of the function. Then in this function, after the dummy read of the IIC data register that triggers the reception of data, the DMA enable bit of the I2C control register is written. /*FUNCTION********************************************************************** * * Function Name : I2C_DRV_MasterReceiveDataDMA * Description   : Performs a non-blocking receive transaction on the I2C bus *                 utilizing DMA to receive the data. * *END**************************************************************************/ i2c_status_t I2C_DRV_MasterReceiveDataDMA(uint32_t instance,                                                const i2c_device_t * device,                                                const uint8_t * cmdBuff,                                                uint32_t cmdSize,                                                uint8_t * rxBuff,                                                uint32_t rxSize,                                                uint32_t timeout_ms) {     assert(instance < I2C_INSTANCE_COUNT);     assert(rxBuff);       I2C_Type * base = g_i2cBase[instance];     i2c_master_state_t * master = (i2c_master_state_t *)g_i2cStatePtr[instance];             /* Return if current instance is used */     OSA_EnterCritical(kCriticalDisableInt);         if (!master->i2cIdle)     {         OSA_ExitCritical(kCriticalDisableInt);         return kStatus_I2C_Busy;     }         master->rxBuff = rxBuff;     master->rxSize = rxSize;     master->txBuff = NULL;     master->txSize = 0;     master->status = kStatus_I2C_Success;     master->i2cIdle = false;     master->isBlocking = true;     OSA_ExitCritical(kCriticalDisableInt);             while(I2C_HAL_GetStatusFlag(base, kI2CBusBusy));     I2C_DRV_MasterSetBaudRate(instance, device);         /* Set direction to send for sending of address. */     I2C_HAL_SetDirMode(base, kI2CSend);       /* Enable i2c interrupt.*/     I2C_HAL_ClearInt(base);     I2C_HAL_SetIntCmd(base, true);       /* Generate start signal. */     I2C_HAL_SendStart(base);       /* Send out slave address. */     I2C_DRV_SendAddress(instance, device, cmdBuff, cmdSize, kI2CReceive, timeout_ms);       /* Start to receive data. */     if (master->status == kStatus_I2C_Success)     {         /* Change direction to receive. */         I2C_HAL_SetDirMode(base, kI2CReceive);                 /* Send NAK if only one byte to read. */         if (rxSize == 0x1U)         {         I2C_HAL_SendNak(base);         }         else         {         I2C_HAL_SendAck(base);         }                 /* Dummy read to trigger receive of next byte in interrupt. */         I2C_HAL_ReadByte(base);                 /* Now set the DMA bit to let the DMA take over the reception. */         I2C_C1_REG(I2C1) |= I2C_C1_DMAEN_MASK;                 /* Don't wait for the transfer to finish. Exit immediately*/     }     else if (master->status == kStatus_I2C_Timeout)     {         /* Disable interrupt. */         I2C_HAL_SetIntCmd(base, false);                 if (I2C_HAL_GetStatusFlag(base, kI2CBusBusy))         {         /* Generate stop signal. */         I2C_HAL_SendStop(base);         }                 /* Indicate I2C bus is idle. */         master->i2cIdle = true;     }         return master->status; } After writing the DMA driver, a DMA specific transfer complete function must be implemented. This is needed in order for the application software to signal to the driver structures that the transfer has been completed and the bus is now idle. In addition, the DMA enable bit needs to be cleared in order for other driver functions to be able to properly use the IIC peripheral. void I2C_DRV_CompleteTransferDMA(uint32_t instance) {     assert(instance < I2C_INSTANCE_COUNT);     I2C_Type * base = g_i2cBase[instance];     i2c_master_state_t * master = (i2c_master_state_t *)g_i2cStatePtr[instance];         I2C_C1_REG(base) &= ~(I2C_C1_DMAEN_MASK | I2C_C1_TX_MASK);     I2C_C1_REG(base) &= ~I2C_C1_MST_MASK;;        /* Indicate I2C bus is idle. */     master->i2cIdle = true; } DMA Configuration Next, the application layer needs a function to configure the DMA properly, and a DMA callback is needed to properly service the DMA interrupt that will be used as well as post a semaphore. But before diving into the specifics of that, it is important to discuss the overall strategy of using the DMA in this particular application. After every transaction, the data register must be serviced to ensure that all of the necessary data is received.  One DMA channel can easily be assigned to service this activity.  After the reception of the second to last data byte, the TXAK bit must be written with a '1' to ensure that the NAK is put on the bus at the appropriate time. This is a little trickier to do.  There are three options: A second dedicated DMA channel can be linked to write the I2C_C1 register every time the I2C_D register is serviced.  This option will require a second array to hold the appropriate values to be written to the I2C_C1 register.  The following figure illustrates this process. The second DMA channel can be linked to write the I2C_C1 register after the second to last data byte has been received.  This option would require that the primary DMA channel be set to receive two data bytes less than the total number of desired data bytes.  The primary DMA channel would also need to be re-configured to receive the last two bytes (or the application software would need to handle this).  However this could be a desirable programming path for applications that are memory constrained as it reduces the amount of memory necessary for your application. The primary DMA channel can be set to receive two data bytes less than the total number of desired data bytes and the core (application software) can handle the reception of the last two bytes.  This would be a desirable option for those looking for a simpler solution but has the drawback that in a system where the core is already handling many other tasks, there may still be issues with writing the TXAK bit on time. This example will focus on option number 1, as this is the simplest, fully automatic solution.  It could also easily be modified to fit the second option as the programmer would simply need to change the number of bytes to receive by the primary DMA and add some reconfiguration information in the interrupt to service the primary DMA channel. DMA Channel #1 The first DMA channel is configured to perform 8-bit  transfers from the I2C data register (I2C_D) to the buffer to hold the desired data.  This channel should transfer the number of desired bytes minus one.  The final byte will be received by the core.  Other DMA configuration bits that are important to set are the cycle steal bit, disable request bit, peripheral request bit (ERQ), interrupt on completion of transfer (EINT), and destination increment (DINC).  It also important to configure the link channel control to perform a link to channel LCH1 after each cycle-steal transfer and LCH1 should be configured for the channel that will transfer from memory to the I2C control register (I2C_C1).  The first DMA channel is configured as shown below. // Set Source Address (this is the UART0_D register       DMA_SAR0 = (uint32_t)&I2C_D_REG(base);             // Set BCR to know how many bytes to transfer       // Need to set to desired size minus 1 because the last will be manually       // read.        DMA_DSR_BCR0 = DMA_DSR_BCR_BCR(destArraySize - 1);             // Clear Source size and Destination size fields.        DMA_DCR0 &= ~(DMA_DCR_SSIZE_MASK                     | DMA_DCR_DSIZE_MASK                     );       // Set DMA as follows:       //     Source size is byte size       //     Destination size is byte size       //     D_REQ cleared automatically by hardware       //     Destination address will be incremented after each transfer       //     Cycle Steal mode       //     External Requests are enabled       //     Interrupts are enabled       //     Asynchronous DMA requests are enabled.       //     Linking to channel LCH1 after each cycle steal transfer       //     Set LCH1 to DMA CH 1.        DMA_DCR0 |= (DMA_DCR_SSIZE(1)             // 1 = 8-bit transfers                    | DMA_DCR_DSIZE(1)           // 1 = 8-bit transfers                    | DMA_DCR_D_REQ_MASK                    | DMA_DCR_DINC_MASK                    | DMA_DCR_CS_MASK                    | DMA_DCR_ERQ_MASK                    | DMA_DCR_EINT_MASK                    | DMA_DCR_EADREQ_MASK                    | DMA_DCR_LINKCC(2)          // Link to LCH1 after each cycle-steal transfer                    | DMA_DCR_LCH1(1)            // Link to DMA CH1                    );       // Set destination address       DMA_DAR0 = (uint32_t)destArray; DMA Channel #2 The second DMA channel, which is the linked channel, should be configured to perform 8-bit transfers that transfer data from an array in memory (titled ack_nak_array in this example) to the I2C control register (I2C_C1).  This channel should also disables requests upon completion of the entire transfer, and enable the cycle-steal mode.  In this channel, the source should be incremented (as opposed to the destination as in the first channel). This channel is configured as shown below: // Set Source Address (this is the UART0_D register       DMA_SAR1 = (uint32_t)ack_nak_array;             // Set BCR to know how many bytes to transfer       // Need to set to desired size minus 1 because the last will be manually       // read.       DMA_DSR_BCR1 = DMA_DSR_BCR_BCR(destArraySize - 1);             // Clear Source size and Destination size fields.        DMA_DCR1 &= ~(DMA_DCR_SSIZE_MASK                     | DMA_DCR_DSIZE_MASK                     );             // Set DMA as follows:       //     Source size is byte size       //     Destination size is byte size       //     D_REQ cleared automatically by hardware       //     Destination address will be incremented after each transfer       //     Cycle Steal mode       //     External Requests are disabled       //     Asynchronous DMA requests are enabled.       DMA_DCR1 |= (DMA_DCR_SSIZE(1)             // 1 = 8-bit transfers                    | DMA_DCR_DSIZE(1)           // 1 = 8-bit transfers                    | DMA_DCR_D_REQ_MASK                    | DMA_DCR_SINC_MASK                    | DMA_DCR_CS_MASK                    | DMA_DCR_EADREQ_MASK                    );             // Set destination address       DMA_DAR1 = (uint32_t)&I2C_C1_REG(base); Once the DMA channels are initialized, the only action left is to configure the interrupts, enable the channel in the DMA MUX, and create the semaphore if it has not already been created.  This is done as shown below. //Need to enable the DMA IRQ       NVIC_EnableIRQ(DMA0_IRQn);       //////////////////////////////////////////////////////////////////////////       // MUX configuration       // Enables the DMA channel and select the DMA Channel Source        DMAMUX0_CHCFG0 = DMAMUX_CHCFG_SOURCE(BOARD_I2C_DMAMUX_CHN); //DMAMUX_CHCFG_ENBL_MASK|DMAMUX_CHCFG_SOURCE(0x31); //0xb1;       DMAMUX0_CHCFG0 |= DMAMUX_CHCFG_ENBL_MASK;             /* Create semaphore */       if(semDmaReady == NULL){         semDmaReady = OSA_EXT_SemaphoreCreate(0);       } Finally, the DMA initialization function also initializes the ack_nak_array.  This is only necessary when implementing the first DMA strategy.  The second DMA strategy would only need to write a single value at the correct time.  The array initialization for strategy #1 is shown below.  Note that the values written to the array are 0xA1 plus the appropriate value of the TXAK bit.  By writing 0xA1, it is ensured that the I2C module will be enabled in master mode with the DMA enable bit set. // Initialize Ack/Nak array       // Need to initialize the Ack/Nak buffer first       for( j=0; j < destArraySize; j++)       {           if(j >= (destArraySize - 2))           {               ack_nak_array[j] = 0xA1 | I2C_C1_TXAK_MASK;           }           else           {               ack_nak_array[j] = 0xA1 & (~I2C_C1_TXAK_MASK);           }       } DMA Interrupt Handler Now a DMA interrupt handler is required.  A minimum of overhead will be required for this example as the interrupt handler simply needs to service the DONE bit and post the semaphore created in the initialization.  The DMA interrupt handler is as follows: void DMA0_IRQHandler(void) {     // Clear pending errors or the done bit     if (((DMA_DSR_BCR0 & DMA_DSR_BCR_DONE_MASK) == DMA_DSR_BCR_DONE_MASK)         | ((DMA_DSR_BCR0 & DMA_DSR_BCR_BES_MASK) == DMA_DSR_BCR_BES_MASK)         | ((DMA_DSR_BCR0 & DMA_DSR_BCR_BED_MASK) == DMA_DSR_BCR_BED_MASK)         | ((DMA_DSR_BCR0 & DMA_DSR_BCR_CE_MASK) == DMA_DSR_BCR_CE_MASK))     {         // Clear the Done MASK and set semaphore, dmaDone         DMA_DSR_BCR0 |= DMA_DSR_BCR_DONE_MASK;         //dmaDone = 1;         OSA_SemaphorePost(semDmaReady);     } } Using your newly written driver function Once all of these items have been taken care of, it is now time for the application to use the functions. It is expected that the DMA will be initialized before calling the DMA receive function.  After the first call, the DMA can be re-initialized every time or could simply be reset with the start address of the arrays and byte counter (this is the minimum of actions that must be performed).  Then the application should ensure that the transaction happened successfully.   Upon a successful call to the I2C_DRV_MasterReceiveDataDMA function, the application should wait for the semaphore to be posted.  Once the semaphore posts, the application software should wait for the Transfer Complete flag to become set.  This ensures that the application does not try to put a STOP signal on the bus before the NAK has been physically put on the bus.  If the STOP signal is attempted out of sequence, the I2C module could be put in an erroneous state and the STOP signal may not be sent.  Next, the I2C_DRV_CompleteTransferDMA function should be called to send the STOP signal and to signal to the driver structures that the bus is idle.  At this point, the I2C transaction is now fully complete and there is still one data byte that hasn't been transferred to the receive buffer.  It is the application's responsibility to perform one last read of the Data register to receive the last data byte of the transaction. /* Now initialize the DMA */    dma_init(BOARD_I2C_INSTANCE, Buffer, ack_nak_buffer, FXOS8700CQ_READ_LEN); //Init DMAMUX       returnValue = I2C_DRV_MasterReceiveDataDMA(BOARD_I2C_INSTANCE, &slave,                                                   cmdBuff, 1, Buffer, FXOS8700CQ_READ_LEN, 1000); if (returnValue != kStatus_I2C_Success)    {        return (kStatus_I2C_Fail);    } /* Wait for the DMA transaction to complete */    OSA_SemaphoreWait(semDmaReady, OSA_WAIT_FOREVER);       /* Need to wait for the transfer to complete */ for(temp=0; temp<250; temp++)     {         if(I2C_HAL_GetStatusFlag(base, kI2CTransferComplete))         {             break;         }     }       /* Now complete the transfer; this includes sending the I2C STOP signal and       clearing the DMA enable bit */    I2C_DRV_CompleteTransferDMA(BOARD_I2C_INSTANCE);       // Once the Transfer is complete, there is still one byte sitting in the Data    // register.      Buffer[11] = I2C_D_REG(g_i2cBase[BOARD_I2C_INSTANCE]); Conclusion To summarize, as consumers demand more and more power efficient technology with more and more functionality, MCU product developers need to cram more functionality in small power efficient MCUs.  Relying on DMA for basic data transfers is one good way to improve performance of smaller power efficient MCUs with a single core. This can be particularly useful in applications where an MCU needs to pull information from and I2C sensor.  To do this, there are three methods of implementing an I2C master receive function in your SDK 1.3 based application. Use two DMA channels.  The first to transfer from the I2C Data register to the destination array.  A second dedicated DMA channel can be linked to write the I2C_C1 register every time the I2C_D register is serviced. Use two DMA channels.  The first to transfer from the I2C Data register to the destination array. The second DMA channel can be linked to write the I2C_C1 register only after the second to last data byte has been received. Use a single DMA channel can be set to receive two data bytes less than the total number of desired data bytes and the core (application software) can handle the reception of the last two bytes. The recommendation of this document is to implement the first or second option as these are fully automatic options requiring the least intervention by the core.
View full article
One of the new features that can be found on the FRDM-K82F is the FlexIO header. It’s be specifically designed to interface with the very cost-efficient OV7670 camera, and uses 8 FlexIO lines to read data from the camera. By using the FlexIO feature, it makes it easy to connect a camera to a Kinetis MCU. A demo is included with Kinetis SDK 1.3 which streams the video data from the camera to a host computer over USB. FlexIO: The FlexIO is a highly configurable module found on select Kinetis devices which provides a wide range of functionality including: • Emulation of a variety of serial/parallel communication protocols • Flexible 16-bit timers with support for a variety of trigger, reset, enable and disable conditions • Programmable logic blocks allowing the implementation of digital logic functions on-chip and configurable interaction of internal and external modules • Programmable state machine for offloading basic system control functions from CPU All with less overhead than software bit-banging, while allowing for more flexibility than dedicated IP. Running the Demo: First you’ll need to setup the hardware. An 18 pin header needs to be installed on the *back* of the board. The camera is oriented this way to allow for use of shields on the top, even if the camera is being used. This way the functionality could be extended with WiFi or LCD shields. After the header is soldered on, plug in the camera. It will look like the following when complete: Next we need to program the K82 device with the example firmware. The software can be found in the Kinetis SDK FRDM-K82F stand-alone release, in the C:\Freescale\KSDK_1.3.0_K82\examples\frdmk82f\demo_apps\usb\device\video\flexio_ov7670 folder. Open the project, compile, and program the example specific for your compiler like done for other examples. Make sure you also compile the USB Device library as well. After programming the K82, unplug the USB cable from J5 (OpenSDA) and plug it into J11 (K82 USB). The board will enumerate as a generic USB video device called “USB VIDEO DEMO”. You can then use this device with any video capture software, like Skype or Lync.  Here's a shot of the clock in my cube: The resolution is 160*120, the video image format is RGB565. You may need to manually adjust the focus by rotating the lens on the camera. The frame rate can also be sped up by modifying line 342 in usb_descriptor.c: 5fps: 0x80,0x84,0x1E,0x00, /* Default frame interval is 5fps */ 10fps:  0x40,0x42,0x0F,0x00, 15fps:  0x2A,0x2C,0x0A,0x00, 20fps:  0x20,0xA1,0x07,0x00, The 160*120 max resolution was determined by the amount internal SRAM of the device, as there is not external RAM on the FRDM-K82F board. More Information: One of many places to buy the OV7670 camera module​ OV7670 Reference Manual​ FlexIO Overview ​ FlexIO Training presented at FTF
View full article
    作者 Shaozhong Liang     YAFFS(Yet Another Flash File System)文件系统是专门针对NAND闪存设计的嵌入式文件系统。在YAFFS中,文件是以固定大小的数据块进行存储的,块的大小可以是512字节、1024字节或者2048字节。这种实现依赖于它能够将一个数据块头和每个数据块关联起来。每个文件(包括目录)都有一个数据块头与之相对应,数据块头中保存了ECC(Error Correction Code)和文件系统的组织信息,用于错误检测和坏块处理。     YAFFS在文件进行改写时总是先写入新的数据块,然后删除旧的数据块,这样即使意外掉电,丢失的也只是这一次修改数据的最小写入单位,从而实现了掉电保护,保证了数据完整性。 YAFFS是为NAND FLASH设计的,它作了以下的假设或定义。     NAND Flash是基于块(block)的,每一个Block大小相同,由整数个chunk组成。每一个Block可单独擦除。一页(page,或chunk)为Flash的分配单元。所有的访问(读或者写)都是基于页(或chunk)的。     当对NAND Flash编程时,只有二进制中的0被编程,而1则“不关心”。比如,一个字节包含的二进制数为1010,那么当编程1001,会导致这两个数的位与操作。结果为1000.这和NOR FLASH不同。     YAFFS 分别用块号和 chunk id 标示块和 chunk 。它将空块(填满0xFF)当作空闲块或者已擦除块。这样,格式化一个YAFFS分区等价于擦除所有未损坏的块。 因此YAFFS最少需要一些函数能够擦除块,读一个页,写一个页。 1. 直接接口(Direct Interface)的相关文件     仅需要提取少量文件。使用yaffs的直接接口,你不需要所有的文件。你实际需要的文件列在下面,其余文件不需要编译。 direct/yaffsfs.c yaffs_guts.c direct/yaffscfg.c yaffs_nand.c yaffs_tagsvalidity.c yaffs_checkptrw.c yaffs_qsort.c yaffs_tagscompat.c yaffs_ecc.c yaffs_packedtags2.c 2. YAFFS  存储设备     YAFFS对文件系统上的所有内容(比如正常文件,目录,链接,设备文件等等)都统一当作文件来处理,每个文件都有一个页面专门存放文件头,文件头保存了文件的模式、所有者id、组id、长度、文件名、Parent Object ID等信息。因为需要在一页内放下这些内容,所以对文件名的长度,符号链接对象的路径名等长度都有限制。前面说到对于NAND FLASH上的每一页数据,都有额外的空间用来存储附加信息,通常NAND驱动只使用了这些空间的一部分,YAFFS正是利用了这部分空间中剩余的部分来存储文件系统相关的内容。以512+16B为一个PAGE的NAND FLASH芯片为例,Yaffs文件系统数据的存储布局如下所示: 0 to 511 数据区域 512 to 515 YAFFS TAG 516 Data status byte 517 Block status byte 坏块标志位 518 to 519 YAFFS TAG 520 to 522 后256字节数据的ECC校验结果 523 to 524 YAFFS TAG 525 to 527 前256字节数据的ECC校验结果     可以看到在这里YAFFS一共使用了8个BYTE用来存放文件系统相关的信息(yaffs_Tags)。这8个Byte的具体使用情况按顺序如下: Bits Content 20 ChunkID,该page在一个文件内的索引号,所以文件大小被限制在2^20 PAGE 即512Mb 2 2 bits serial number 10 ByteCount 该page内的有效字节数 18 ObjectID 对象ID号,用来唯一标示一个文件 12 Ecc, Yaffs_Tags本身的ECC校验和 2 Unused     其中Serial Number在文件系统创建时都为0,以后每次写具有同一ObjectID和ChunkID的page的时候都加一,因为YAFFS在更新一个PAGE的时候总是在一个新的物理Page上写入数据,再将原先的物理Page删除,所以该serial number可以在断电等特殊情况下,当新的page已经写入但老的page还没有被删除的时候用来识别正确的Page,保证数据的正确性。 ObjectID号为18bit,所以文件的总数限制在256K即26万个左右。     由于文件系统的基本组织信息保存在页面的备份空间中,因此,在文件系统加载时只需要扫描各个页面的备份空间,即可建立起整个文件系统的结构,而不需要像JFFS1/2 那样扫描整个介质,从而大大加快了文件系统的加载速度。     一个YAFFS设备是一个逻辑设备,它代表了一个物理设备的部分或整体。你可以认为它是一个Nand上的一个“分区”。比如,该分区可能覆盖整个NAND,也许只是一半,而另外一半就是另一个Yaffs_Device.它也可以用于你使用一个非flash设备(比如RAM)来测试的情况下。 一个Yaffs_Device记录了起始和结束块。通过改变它的起始和结束块,你就可以在同一个物理设备上使用不止一个的Yaffs_Device。 这里将需要你自己建立的Yaffs_Device结构的数据域列出,其他数据域由Yaffs自动创建。 int nDataBytesPerChunk     如其名,这是每一个chunk的字节数,还记得吧,在yaffs术语中,一个页就是一个chunk,因而它也是一页的字节数。它是数据字节数,即不包含OOB的数据。比如一页时2048字节+64字节的OOB,那么数值nDataBytesPerChunk为2048。 int nChunksPerBlock     物理Nand设备中每页包含的chunk(就是Nand上的页)的数目,最少是2。 int spareBytesPerChunk     空闲域(spare area)大小,比如:每个chunk(页)的OOB字节数。 int startBlock     该逻辑Yaffs_Device设备第一个块的块号(而字节地址),注意,yaffs需要第一个块是空闲的,因此你不可以设置该变量为0,如果设置为0,Yaffs会给它加1,并且会在结束块号上也加1,在你设置设备从块0开始,到最后一个块结束,这意味着yaffs试图写一个不存在的块,从而出现错误。 int endBlock     该逻辑Yaffs_Device设备的最后一个块号。如果startBlock为0,那么yaffs会使用endBlock+1,至少使startBlock+nReservedBlocks+2 int nReservedBlocks     这是YAFFS必须保留,用于垃圾回收和块错误恢复的可擦除块的数目。至少是2,但是5更好。如果你使用一个不会损坏的介质,比如RAM或者RAM盘,或者主机文件系统模拟,那么可以是2。 int nShortOpCaches     配置当前设备YAFFS Cache项的数目。0值表示不使用cache。对于大多数系统,推荐使用10到20之间的一个数值。不能大于YAFFS_MAX_SHORT_OP_CACHES定义的数值。 int useNANDECC     这是一个标志,用于指示是由yaffs执行ECC计算,还是由NAND驱动程序来执行ECC计算。(译者注:此数值取0,则使用yaffs来执行ECC计算,软件ECC计算。如果想要使用硬件ECC校验时,应该设置为1,并且在NAND驱动程序中加入硬件ECC校验的代码。) void *genericDevice     这是一个指针,它应该指向任何数据,底层NAND驱动程序需要知道以从物理设备读、写。 int isYaffs2     我们使用的是否YAFFS2版本? int inbandTags     是否为OOB区,如果不是,那么它为真,仅用于yaffs2 u32 totalBytesPerChunk     这个名字可能有点误导人,它应该等于nDataBytesPerChunk ,而非其名字暗示的nDataBytesPerChunk + spareBytesPerChunk。如果inbandTags为真,那么yaffs设置nDataBytesPerChunk,因此有足够的空闲空间存储数据,yaffs会在空闲域中正常存储。 write/readChunkWithTagsFromNAND, markNANDBlockBad queryNANDBlock 这些都是函数指针,你需要提供这些函数来给YAFFS,读写nand flash。 3.NAND Flash 访问函数 int (*writeChunkWithTagsToNAND) (struct yaffs_DeviceStruct * dev, int chunkInNAND, const u8 * data, const yaffs_ExtendedTags * tags);   dev: 要写入的yaffs_Device逻辑设备. chunkInNAND: 将chunk写入的页 Data: 指向需要写入的数据的指针 tags: 未压缩(打包)的OOB数据 Return: YAFFS_OK / YAFFS_FAIL 该函数将页(chunk)写入nand中,向nand中写入数据。数据和标签(tags)永远不应为 NULL. chunkInNand 是将要写入的页的页号,而不是需要转换的地址。 int (*readChunkWithTagsFromNAND) (struct yaffs_DeviceStruct * dev, int chunkInNAND, u8 * data, yaffs_ExtendedTags * tags);  dev: 要写入的yaffs_Device逻辑设备. chunkInNAND: 将chunk读入的页 Data: 指向需要读入的数据的缓冲区指针 tags: 指向未压缩(打包)的OOB数据的缓冲区指针 Return: YAFFS_OK / YAFFS_FAIL 该函数执行上一个函数的相反的功能,首先,读取数据和OOB字节,接着将这些输入放在一个由参数data指向的缓冲区中 int (*markNANDBlockBad) (struct yaffs_DeviceStruct * dev, int blockNo);   dev: 要写入的yaffs_Device逻辑设备. blockNo: 要标记的块. Return: YAFFS_OK / YAFFS_FAIL int (*queryNANDBlock) (struct yaffs_DeviceStruct * dev, int blockNo, yaffs_BlockState * state, u32 *sequenceNumber);   dev: 要写入的Yaffs_Device逻辑设备. blockNo: 要标记的块. state: Upon returning this should be set to the relevant state of this particular block. Sequance number: 该块的顺序号(The Sequence number),为0表示此块未使用 Return: YAFFS_OK / YAFFS_FAIL     它应检查一个块是否是有效的。如果在OOB中设置了坏块标记,那么*state应该被赋值为YAFFS_BLOCK_STATE_DEAD,*sequenceNumber赋值为0,然后返回YAFFS_FAIL。     如果该块没坏,那么应解压缩标签。标签解压缩后,若发现chunk已使用(查看tags.chunkUsed),则*sequenceNumber应赋值为tags.sequenceNumber,*state赋值为YAFFS_BLOCK_STATE_NEEDS_SCANNING,否则该块未使用,则*sequenceNumber赋值为0,*state赋值为YAFFS_BLOCK_STATE_EMPTY 4. YAFFS的缓存机制     由于NandFlash是有一定的读写次数的,所以在对一个文件进行操作的时候往往是先通过缓冲进行,对最后一次性写入NandFlash,这有效的减少了用户对NandFlash的频繁操作,延长了NandFlash的寿命。下面大致说一下YAFFS的缓存机制: 4.1.首先在yaffs_mount的时候会对yaffs_dev这个结构体进行注册,和缓冲部分相关的有: dev->nShortOpCaches//这个变量决定了有多少个缓冲,因为缓冲会大量的占用堆栈的空间,所以在yaffs不建议缓冲的数量很大,即使你填一个很大的数,系统也不会超过YAFFS_MAX_SHORT_OP_CACHES的总数。 yaffs_ChunkCache *srCache;//缓冲区的首地址,dev->srCache = YMALLOC( dev->nShortOpCaches * sizeof(yaffs_ChunkCache));下面介绍一下缓冲区这个结构体的组成: typedef struct { struct yaffs_ObjectStruct *object;//一个缓冲区对应一个文件 int chunkId; int lastUse; //通过lastUse来 int dirty; //标志了这一个缓冲区是否被使用 int nBytes; __u8 data[YAFFS_BYTES_PER_CHUNK];//数据区 } yaffs_ChunkCache; 4.2.什么时候用到缓冲区?        用到缓冲区最多的地方显而易见是对已经创建的文件进行写操作。而且是需要写的大小和512不一致的时候,这是因为如果是刚好512的话,系统会直接写入NandFlash中。对于小于512的系统首先会调用yaffs_FindChunkCache(in,chunk)这个函数来判断in这个object是否在缓冲区中存在。如果存在会调用已有缓冲区进行操作。当然如果是第一次对一个object进行操作,肯定在缓冲区中是不存在对应它的空间的,因此系统会调用yaffs_GrabChunkCache函数为此次操作分配一个缓冲区。 5. 应用层接口     YAFFS为连接的应用程序提供了一组函数。大部分跟标准C库函数,如open/close一致,只是增加了yaffs_前缀,如 yaffs_open. 这些函数定义在direct/yaffsfs.h中。     初始化yaffs来完成读写,你必须在每个你要使用的yaffs设备上调用yaffs_mount。比如yaffs_mount(”/boot”)。这可以在系统启动的时候执行,如果存在一个操作系统,那么程序需要考虑这点。在你完成使用的时候,你也需要调用yaffs_umount函数,这样yaffs就会将它需要状态写入磁盘。 如果读写文件的应用层接口已经存在,你可以根据相关的操作系统调用来封装相关的函数调用。 1 yaffs_mount( ) 功能说明:加载指定器件。 输入参数:path    要加载的器件。 输出参数:无。 返回值: 表明加载的状态。 调用的函数:yaffsfs_FindDevice( )、yaffs_GutsInitialise( )。 2 yaffs_open( ) 功能说明:按照指定方式打开文件。 输入参数:path    文件的绝对路径;           Oflag   打开的方式;           Mode    文件许可模式。 输出参数:无。 返回值:句柄。 调用的函数:yaffsfs_GetHandle( )、yaffsfs_FindDirectory( )、yaffs_MknodFile( )、yaffsfs_PutHandle( )、yaffs_ResizeFile( )、yaffsfs_FindObject( )。 3 yaffs_write( ) 功能说明:根据打开文件的句柄,从指定数组处读指定字节写入文件中。 输入参数:fd      要写入的文件的句柄;           Buf     要写入的数据的首地址;           Nbyte   要写入的字节数。 输出参数:无。 返回值: 写入了的字节数。 调用的函数:yaffs_WriteDataToFile( )、yaffsfs_GetHandlePointer( )、yaffsfs_GetHandleObject( ) 4 yaffs_read( ) 功能说明:根据打开文件的句柄,从文件中读出指定字节数据存入指定地址。 输入参数:fd       要读出的文件的句柄;           Buf      读出文件后要存入的数据的首地址;           Nbyte    要读出的字节数。 输出参数:无。 返回值: 读出了的字节数。 调用的函数:yaffs_ReadDataFromFile( )、yaffsfs_GetHandlePointer( ) 5 yaffs_close( ) 功能说明:关闭已经打开的文件句柄,yaffs 有缓冲机制,当调用yaffs_close()关闭文件之后能够保证将内容写入nandflash。 输入参数:fd    需要关闭的文件的句柄; 输出参数:无。 返回值:无。 6. YAFFS在MQX的应用案例     YAFFS提供了直接调用模式,可以方便移植到 none-OS或者light-weighted OS中。附件是将YAFFS移植到Freescale MQX实时操作系统的源代码和工程,可以在II型集中器的Demo Board上运行。     初步的测试表明YAFFS工作正常,能够完成创建目录,创建/删除文件,读/写文件操作等。 YAFFS非常适合none-OS或者是light-weighted OS,使用YAFFS需要关注的是RAM的消耗,适合小量文件(<20)。 如果不想使用MQX默认的MFS(FAT32文件系统),YAFFS可以作为一个文件系统的备选方案。
View full article
Here you can find the code and project files for the GPIO example, in this example the 3 colors of the RGB led are turned on sequentially when the SW2 push button is pressed, the led pin definition is shared throughout all the freedom platforms. The wait function can be defined in seconds, miliseconds or microseconds. Code: #include "mbed.h" //Delay declared in seconds /*GPIO declaration*/ DigitalOut Red(LED1);         DigitalOut Green(LED2); DigitalOut Blue(LED3); DigitalIn sw2(SW2); int main() {     /*Leds OFF*/     Red=1;     Green=1;     Blue=1;         while(1)     {         if(sw2==0)         {             Red = 0;             wait(.2);             Red = 1;             wait(1);                                Green=0;             wait(.2);             Green=1;             wait(1);                         Blue=0;             wait(.2);             Blue=1;             wait(1);         }     } }
View full article
Here you can find both the code and project files for the PWM project, in this example a single PWM channel belonging to the Flextimer 0 (PTC10/FTM_CH12) is enabled to provide a PWM signal with a 500ms period, the signal's duty cycle increases its period every 100ms, to visually observe the signal connect a led from the A5 pin in the J4 connector to GND (J3, pin 14). Code: #include "mbed.h" //PWM output channel PwmOut PWM1(A5); int main() {     PWM1.period_ms(500);     int x;     x=1;         while(1)     {         PWM1.pulsewidth_ms(x);         x=x+1;         wait(.1);         if(x==500)         {             x=1;         }     } }
View full article
Latest version of the AN2295 universal bootloader includes support for IAR 7.6 IDE. - added support for Kinetis E MCUs - Kinetis K,L,M,E,W,V support
View full article
        在我们嵌入式工程应用中,中断作为最常用的异步手段是必不可少的,而且在一个应用程序中,一个中断往往是不够用的,多个中断混合使用甚至多级中断嵌套也经常会使用到,而这样就涉及到一个中断优先级的问题。         以我们最熟悉的Cortex-M系列为例,我们知道ARM从Cortex-M系列开始引入了NVIC的概念(Nested Vectors Interrupts Controller),即嵌套向量中断控制器,以它为核心通过一张中断向量表来控制系统中断功能,NVIC可以提供以下几个功能: 1)可嵌套中断支持; 2)向量中断支持; 3)动态优先级调整支持; 4)中断可屏蔽。         抛开其他不谈,这里我们只说说中断优先级的问题。我们知道NVIC的核心工作原理即是对一张中断向量表的维护上,其中M4最多支持240+16个中断向量,M0+则最多支持32+16个中断向量,而这些中断向量默认的优先级则是向量号越小的优先级越高,即从小到大,优先级是递减的。但是我们肯定不会满足于默认的状态(人往往不满足于约束,换句俗话说就是不喜欢按套路出牌,呵呵),而NVIC则恰恰提供了这种灵活性,即支持动态优先级调整,无论是M0+还是M4除了3个中断向量之外(复位、NMI和HardFault,他们的中断优先级为负数,它们3个的优先级是最高的且不可更改),其他中断向量都是可以动态调整的。         不过需要注意的是,中断向量表的前16个为内核级中断,之后的为外部中断,而内核级中断和外部中断的优先级则是由两套不同的寄存器组来控制的,其中内核级中断由SCB_SHPRx寄存器来控制(M0+为SCB_SHPR[2:3],M4为SCB_SHPR[1:3]),外部中断则由NVIC_IPRx来控制(M0+为NVIC_IPR[0:7],M4为NVIC_IPR[0:59]),如下图所示: M0+中断优先级寄存器: M4中断优先级寄存器:         其中M4所支持的动态优先级范围为0~15(8位中只有高四位[7:4]才有效),而M0+所支持的动态优先级范围则为0~3(8位中只有高两位[7:6]才有效),而且秉承着号越小优先级越高的原则(0最高,15或3为最小),同时也间接解释了为什么复位(-3)、NMI(-2)和HardFault(-1)优先级最高的原因,很简单,人家都是负的了,谁还能比他们高,呵呵,而且这三位中复位优先级最高,NMI其次,HardFault最低(这个最低仅限于这三者)。 下面给出个ARM CMSIS库中关于M0+和M4中断优先级设置的API函数NVIC_SetPriority(IRQn_Type IRQn, uint32_t priority)实现供大家来参考: M0+: NVIC_SetPriority(IRQn_Type IRQn, uint32_t priority) {   if(IRQn < 0) {     SCB->SHP[_SHP_IDX(IRQn)] = (SCB->SHP[_SHP_IDX(IRQn)] & ~(0xFF << _BIT_SHIFT(IRQn))) |         (((priority << (8 - __NVIC_PRIO_BITS)) & 0xFF) << _BIT_SHIFT(IRQn)); }  /* set Priority for Cortex-M  System Interrupts */   else {     NVIC->IP[_IP_IDX(IRQn)] = (NVIC->IP[_IP_IDX(IRQn)] & ~(0xFF << _BIT_SHIFT(IRQn))) |         (((priority << (8 - __NVIC_PRIO_BITS)) & 0xFF) << _BIT_SHIFT(IRQn)); }   /* set Priority for device specific Interrupts  */ } M4: void NVIC_SetPriority(IRQn_Type IRQn, uint32_t priority) {   if(IRQn < 0) {     SCB->SHP[((uint32_t)(IRQn) & 0xF)-4] = ((priority << (8 - __NVIC_PRIO_BITS)) & 0xff); } /* set Priority for Cortex-M  System Interrupts */   else {     NVIC->IP[(uint32_t)(IRQn)] = ((priority << (8 - __NVIC_PRIO_BITS)) & 0xff);    }        /* set Priority for device specific Interrupts  */ }
View full article
This document covers some of the more common questions about the new Kinetis K8x family. Any new specific issues or questions should be posted into it's own thread, and will be added to this document as appropriate. Kinetis K80 Basics What is the K8x family? It is a new Kinetis family of Cortex-M4F devices, running up to 150MHz, that include 256K of Flash and 256K of SRAM. It features FS USB, SDRAM, QuadSPI, SPI, I2C, LPUART, and much much more. How does the Kinetis K8x family differ from other Kinetis K families? The K8x family offers the same advantages and compatibility as other Kinetis K families, but also offers several new features not found on other Kinetis K families: QuadSPI Support Dual Voltage Domains (independent VDDIO domain down to 1.8V for QuadSPI or other interfaces) EMVSIM (Euro, MasterCard, Visa Serial Interface Module) FlexIO Additionally the K81 and K82 families offer the following new security modules: LTC (Low Power Trusted Cryptography) Encryption / Decryption algorithms in hardware (as opposed to using mmCAU s/w libs) OTFAD (On The Fly AES Decryption) Zero latency decryption when executing encrypted code from QuadSPI Secure RAM 2KB of Secure Session RAM Because of the addition of a second voltage domain and QuadSPI, there is no hardware pin compatibility with previous Kinetis derivatives. However there is significant module and enablement re-use, so if you’re familiar with other Kinetis devices, it will be easy to get started with the K80. Where can I find reference manuals, datasheets, and errata? These can be found on the K8x documentation pages. Detailed information on the K81 is under NDA, so please contact your NXP sales representative for those documents. What’s the difference between the different K8x devices? K80 is the base version, which includes QuadSPI controller, SDRAM controller, FS USB, and much more. K81 adds DryIce Tamper Detect and the LTC/OTFAD modules K82 adds just the LTC/OTFAD modules K80 and K82 families have the same pin out for their respective packages. The pinout for K81 is slightly different but can still be compatible. What boards are available to evaluate the K80 family? FRDM-K82F: A Freedom board with a 100LQFP K82 device. Also includes dual QuadSPI, touch pad, Arduino compatible footprint, and FlexIO header compatible with OV7670 camera. TWR-K80F150M: A Tower board with 121XFBGA K80 device. Includes dual QuadSPI, SDRAM, EVMSIM, SDCard holder, touch pads, and more. TWR-POS-K81: A Point of Sale reference design board in tower form factor. This board is only available via your NXP sales representative. The K8x MCU Family Hardware Tools selection guide has more details on board differences. What packages are available? The 100 LQFP and 121 XFBGA packages are lead packages available today. The 144 LQFP package and the WLCSP are part of the Package Your Way (PYW) program, and you should contact your NXP sales representative if interested in those packages. What is the difference between K8x and KL8x families? The KL8x family shares many of the same features as the K8x family. The biggest differences are that the KL8x family uses the Cortex-M0+ core (instead of Cortex-M4F), has a lower max clock speed, and has less internal Flash and RAM. It also reduces the instances of peripherals available, but still includes QuadSPI, FlexIO, LTC, and BootROM peripherals like on the K80. See the KL8x Fact Sheet for more details. KL8x devices will be available in the first quarter of 2016. Software/Tools Where can I find instructions and details on the hardware used to evaluate the K8x family? FRDM-K82F: http://nxp.com/frdm-k82f/startnow​ TWR-K80F150M: http://nxp.com/twr-k80f150m/startnow ​ Which version of Kinetis SDK supports the K8x family? Kinetis Software Development Kit (KSDK) support is split depending on the evaluation platform. For TWR-K80F150M, support can be found in the Kinetis SDK 1.3 Mainline Release. For FRDM-K82F, support can be found in the Kinetis SDK FRDM-K82F Stand-alone release. Note that the FRDM-K82 standalone release is truly standalone, and does not require the mainline release to be installed. How do I run the FRDM-K82F OV7670 camera demo? See this Community post: https://community.freescale.com/docs/DOC-329438 How can I use the micro SD card reader on the TWR-K80F150M? Because the SD card signals are shared with the QuadSPI signals, the SD card slot is not connected by default. See section 3.14 of the TWR-K80F150M User Guide for details on how to connect it, with the understanding that QuadSPI will not be available on the board while using SDHC. How do I use the SDRAM on the TWR-K80F150M? See section 3.9 of the TWR-K80F150M User Guide. Due to the layout of the board, the OpenSDA UART feature cannot be used while running the SDRAM as jumpers J6 and J8 need to be removed. QuadSPI What is QuadSPI Flash? Why should I use it? QuadSPI is a name for a popular type of serial NOR flash memory that is SPI compatible, but also allows for multiple data lines (up to 4 per device, or 8 if done in parallel) with bi-directional data for increased memory bandwidth. The QuadSPI controller on the K8x also allows for Execute-In-Place (XIP) mode so that code can be executed out of this external memory. QuadSPI memory can be used for either extra memory storage or for extra code space, or a combination of both. After initialization, it appears as a readable area of memory starting at 0x6800_0000 (as well as at the alias regions). How can I program the QuadSPI? There is an example application in Kinetis SDK that shows how to program the QuadSPI at C:\Freescale\KSDK_1.3.0\examples\twrk80f150m\driver_examples\qspi For programming an entire application, the ROM bootloader can be used. Details are in the K80 Bootloader Tools Package. The Kinetis Bootloader QuadSPI User's Guide that comes as part of that package describes all the steps needed to get up and running with QuadSPI. There is also an example Kinetis SDK application that runs out of QuadSPI at C:\Freescale\KSDK_1.3.0\examples\twrk80f150m\demo_apps\hello_world_qspi_alias What performance tips are there if doing QuadSPI XIP? A few key performance factors: Ensure both the data and instruction cache is enabled Use as many data lines as possible (4, or 8 if available in dual/octal modes) Use DDR mode Any critical code should be placed in Flash/RAM for fastest performance If using XIP, code should be executed out of the QuadSPI aliased address space which starts at 0x0400_0000. A more detailed app note is under development. How do I debug code located in QuadSPI? You must make use of the aliased QuadSPI address space at 0x0400_0000. There is an example of this in the hello_world_qspi_alias example in Kinetis SDK. Due to the architecture of the M4 core on Kinetis, breakpoints cannot be set in the 6800_0000 address space, which is why the alias address space is provided. What app notes are available for the QuadSPI? Because the QuadSPI module found on the K8x family has also been used on other NXP devices, there are some app notes available that can be useful for QuadSPI development. Note that some of the implementation details and features as described in the app notes will be different for K8x, so please use the K8x reference manual for full details. AN4186​ AN4512​ AN4777​ ROM Bootloader Where can I find more information on the bootloader that comes built into the silicon of the K8x family? Download the K80 Bootloader Tools package. If interested in QuadSPI, the Kinetis Bootloader QuadSPI User's Guide that comes as part of that package describes all the steps needed to get up and running with QuadSPI. The other information found on the Kinetis Bootloader website is also useful as this is what the ROM Bootloader is based off of. What interfaces does the ROM Bootloader support? The ROM Bootloader on the K8x family can interface via LPUART, I2C, SPI, or USB HID (via BLHost) to erase and program both the internal flash and/or QuadSPI flash. This is the same bootloader found on other Kinetis devices, but also includes some more advanced features to support QuadSPI. How can I enter bootloader mode? By default, when using a Kinetis SDK project, the bootloader is disabled and the code immediately jumps to the address in Flash pointed at location 0x4. By asserting the NMI pin at reset though, the part can be forced to enter bootloader mode. This is useful for programming the QuadSPI or interfacing with the bootloader in other ways. This feature is controlled via the FOPT[BOOTPIN_OPT] bit, which the Kinetis SDK code sets to '0' to enable the NMI pin to enter bootloader mode. The NMI button on each board is: FRDM-K82F: SW2 TWR-K80F150M: SW2 The FOPT register (at 0x40C) can be modified to always go into Bootloader mode if desired. Details are in boot chapter of the K80 reference manual. Where is the bootloader configuration data found in Kinetis SDK? The Bootloader Configuration Area (BCA), which begins at address 0x3C0, is defined in C:\Freescale\KSDK_1.3.0\platform\devices\MK80F25615\startup\system_MK80F25615.c starting on line 133. You must also add the define BOOTLOADER_CONFIG in the project settings to let the linker files know to program this BCA area. The FOPT configuration register (at 0x40D) is defined in C:\Freescale\KSDK_1.3.0_K82\platform\devices\MK82F25615\startup\<compiler>\startup_MK80F25615.s and by default is set to 0x3D which disables the bootloader, but does enable the option to enter bootloader via the NMI pin at reset (see previous question) How can I use the UART port on the FRDM-K82F with the BootROM? The OpenSDA/UART lines on the FRDM-K82F use LPUART4, which is not used by the BootROM. If you would like to use the serial UART lines to interact with the BootROM, you can blue wire a connection from either J24 or J1, and connect to R32 (RX) and R36 (TX). This was due to muxing trade-offs. The OpenSDA/UART lines on the TWR-K80F150M are connected to UART1 and thus no modification is necessary for that board. Also keep in mind that you can use the USB interface with the BLHost tool on both boards with no modification. The examples in Kinetis SDK setup the QuadSPI Configuration Block (QCB) data using a qspi_config.bin file. How can I generate my own custom QCB file? There is a C file that come as part of Kinetis SDK (C:\Freescale\KSDK_1.3.0\examples\twrk80f150m\demo_apps\hello_world_qspi\qspi_config_block_generator.c) or in the KBoot zip file, that can be compiled with various toolchains on a host computer, that will then produce a .bin file. You could import this file, and then after compilation, run it, and it will write out the new .bin to your hard drive. There is a tool under development that simplifies this process by reading in that example .bin file and then you can modify the fields in the app, and then it will write out the modified .bin file. Can I jump directly to QuadSPI for Execute in Place (XiP) after booting? Yes. However note that you must still put the Bootloader Configuration Area (BCA) into internal flash. And you also may want to put the QuadSPI Configuration Block (QCB) in flash as well since it needs to be read before the QuadSPI is setup. Thus even if all your code is in QuadSPI address space, the internal flash must also be written at least once to put in the configuration data. Once you have that set though, then you can develop code by only programming the QuadSPI address space. Troubleshooting I’m having debugger connection issues when using an external debugger, like a Segger JLink. Why? It’s likely that the OpenSDA circuit is interfering, and thus needs to be isolated via jumpers on the board. For TWR-K80F150M: Pull J16 and J17 For FRDM-K82F: Pull J6 and J7 Also make sure you are using the correct debug header for the K8x device on the board: For TWR-K80F150M: J11 For FRDM-K82F: J19 Where is the CMSIS-DAP/OpenOCD debug configuration for the K8x family in Kinetis Design Studio? KDS 3.0 does not support programming the K8x family via the CMSIS-DAP interface. You will need to change the OpenSDA app on the board to either J-Link or P&E as described in the K8x Getting Started guides (Part 3). I can't get OpenSDA on the FRDM-K82F into bootloader mode. Make sure jumper J23 is on pins 1-2 to connect the reset signal to the OpenSDA circuit. On some early versions of the board this was incorrectly installed on pins 2-3 instead. When using IAR with the default CMSIS-DAP debug interface, I sometimes get the error: “Fatal error: CPU did not power up” This is an issue in some older versions of IAR. Upgrade to at least version 7.40.5 which fixes this. When using KDS with the JLink interface with the FRDM-K82F board, I get an error. If you see the error "The selected device 'MK82FN256XXX15' is unknown to this version of the J-Link software." it's because the J-Link driver that comes with KDS 3.0.0 does not know about the K82 family. You can either select a MK80FN256XXX15 device (which is compatible with the K82 on the board) or update the JLink software by downloading and installing the latest JLink Software and documentation pack. At the end of the installation process it will ask to update the DLLs used by the IDEs installed on your computer, so make sure to check the KDS checkbox on that screen. I’m using the P&E OpenSDA App and debugging is not working. I get either "Error reading data from OpenSDA hardware. E17925" or “The system tried to join a drive to a directory on a joined drive” in KDS If using IAR, make sure you have the latest version (7.40.7 or later) If using KDS, you need to update the P&E plugin in KDS. Go to Help->Check for Updates, and select the P&E debug update. Make sure not to select the other debugger updates as it will break it in KDS 3.0.0 (see this thread)
View full article
USB secondary ISP bootloader for LPC11U68  Overview        A Secondary Bootloader (SBL) is a piece of code that allows a user application code to be downloaded using alternative channels other than the standard UART0 used by the internal bootloader (on chip). Possible secondary bootloaders can be written for USB, Ethernet, SPI, SSP, CAN, and even I/Os. The secondary bootloader utilizes IAP as a method to update the user’s application code.        The internal bootloader is the firmware that resides in the microcontroller’s boot ROM block and is executed on power-up and resets. After the boot ROM’s execution, the secondary bootloader would be executed, which will then execute the user application.      The purpose of this document is to use USB as an example for developing the secondary bootloader and the code was tested using the LPCXpresso 11U68 evaluation board.       The MSCD presents easy integration with a PC‘s operating systems. This class allows the embedded system’s flash memory space be represented as a folder in Windows/Linux. The user can update the flash with the binary image using drag and drop, so the following sections will present a guideline for development and implementation of the USB secondary bootloader design, configuration, and test.      USB secondary bootloader code is base on the USB Mass Storage Class demo. However in this application note, we do not attempt to explain how the Mass Storage Class is implemented. Fig 1 LPCXpresso Board for LPC11U68 Setup file (sbl_config.h)       This file configures the secondary bootloader. The user should change this according to their application.       Some definitions and explanation: MAX_USER_SECTOR – This parameter is device dependent. In a 256 KB device, it will be 29 sectors, however the size of the last 5 sectors become the 32 KB instead of the 4 KB, so in the application, MAX_USER_SECTOR chooses 23 (Fig 2). CRP – Code Read Protection. This parameter allows select the desired CRP level. Choosing CRP3, the primary bootloader’s entry mechanism check will be bypassed. Fig 3 for CRP details. Fig 2 Flash sectors in LPC11U68 Fig 3 Code Read Protection (CRP) Secondary bootloader entry        The boot sequence shown below is used when entering the secondary USB bootloader. Fig 4 Using an entry pin      The secondary USB bootloader will check the status of a GPIO pin to determine if it should enter into programming mode. This is the easiest way since no post processing is needed. And this secondary bootloader uses P0.16. Automatic secondary bootloader entry       If the secondary USB bootloader detects that no user application is present upon reset, it will automatically enter programming mode. ISP entry disabled     If the secondary USB bootloader detects that a user application has already been installed and that CRP is set to level 3, then it will not enter ISP mode. Bootloader size        Since the bootloader resides within user programmable flash, it should be designed as small as possible. The larger the secondary USB bootloader is the less flash space is available to the user application. By default, the USB bootloader has been designed to fit within the first two flash sectors (Sector 0-1) so that the user application can start from sector 2. Code placement in flash       The secondary bootloader is placed at the starting address 0x0 so that it will be executed by the LPC11U68 after reset. Flash programming is based on a sector-by-sector basis. This means that the code for the user application should not be stored in any of the same flash sectors as the secondary bootloader and for efficient use of the flash space, the user application should be flashed into the next available empty sector after the bootloader.        In the application, the start sector is 3 (0x0000_3000) which is used to store the user application code. User application execution        If the SW2 button is not depressed, the secondary bootloader will start the execution of the user application. Execution of the user application is performed by updating the stack pointer (SP) and program counter (PC) registers. The SP points to the new location where the user application has allocated the top of its stack .The PC on the other hand contains the location of the first executable instruction in the user application. From here on the CPU will continue normal execution and initializations specified on the user application. By default, the bootloader uses 2 flash sectors. Therefore, to utilize the remaining flash, the secondary bootloader will look for the user application at 0x00003000 Handing interrupts      The LPC11U68 contains a NVIC (Nested Vectored Interrupt Controller) that handles all interrupts. When an interrupt occurs the processor uses the vector table to locate the address of the handler.      On the LPC11U68 the vector table is located in the same area of flash memory as the secondary bootloader. The secondary bootloader is designed to be permanently resident in flash memory and therefore it is not possible to update the contents of the vector table every time a new application is downloaded.       The Cortex-M3 core allows the vector table to be remapped; however this is not the case with the Cortex-M0. Because of this, the secondary bootloader has been designed to redirect the processor to the handler listed in a vector table located in the application area of flash memory, see Fig 5. Fig 5 User application       To execute the user application the secondary USB bootloader will load the new SP and PC values into their respective registers, allowing the CPU to execute the new code correctly. Therefore, the user application must be built so that it can run from that starting address. In the application, this address is 0x00003E00. So relocate the user application storage area by following corresponding IDE’s User Guide.  Testing  Creating the binary file             In this application, I build the demos_switch_blinky which is from the LPCOpen library to create the binary which is compatible with the secondary USB bootloader. The binary see Table 1. 08 04 00 10 B5 09 00 00 07 07 00 00 9B 09 00 00 00 00 00 00 00 00 00 00 00 00 00 00 A1 E1 FF EF 00 00 00 00 00 00 00 00 00 00 00 00 A7 09 00 00 00 00 00 00 00 00 00 00 E5 09 00 00 27 03 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 01 03 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E3 09 00 00 E1 09 00 00 FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF FF 38 B5 63 4C 25 68 28 07 07 D5 96 20 E0 60 61 48 00 78 00 28 01 D1 00 F0 F7 F8 20 68 0C 21 29 40 01 43 21 60 31 BD 38 B5 5A 4C A0 78 40 1C A0 70 C0 B2 65 28 34 DB 00 25 A5 70 20 78 00 28 2F D0 60 78 00 28 03 D0 02 28 16 D0 0A D3 20 E0 01 21 00 F0 CA F8 00 21 01 20 00 F0 C6 F8 00 21 02 20 13 E0 01 21 01 20 00 F0 BF F8 00 21 00 20 00 F0 BB F8 00 21 02 20 08 E0 01 21 00 F0 B5 F8 00 21 01 20 00 F0 B1 F8 00 21 01 20 00 F0 AD F8 00 E0 65 70 60 78 40 1C 60 70 C0 B2 03 28 00 DB 65 70 31 BD F8 B5 00 F0 36 F9 00 F0 C2 F8 3A 48 01 68 02 22 91 43 01 60 01 68 38 4A 0A 40 02 60 35 4F 01 20 38 70 36 48 00 68 0A 21 00 F0 2B F9 1E 21 00 F0 28 F9 40 1E 00 26 80 21 49 04 88 42 0C D2 30 49 48 60 30 48 02 68 12 02 12 0A C0 23 1B 06 13 43 03 60 8E 60 07 20 08 60 01 20 2B 49 08 60 23 4C 20 00 00 F0 18 F9 29 48 01 68 80 22 12 03 0A 43 02 60 20 68 01 21 01 43 21 60 20 68 01 21 88 43 20 60 20 68 80 21 88 43 20 60 A6 60 FA 20 80 00 60 60 20 68 40 21 01 43 21 60 20 68 80 21 01 43 21 60 20 68 80 20 80 04 1A 49 08 60 20 68 30 21 01 43 21 60 18 4D 28 78 00 28 12 D1 38 78 00 28 0E D0 00 21 00 20 00 F0 3E F8 00 21 01 20 00 F0 3A F8 00 21 02 20 00 F0 36 F8 FA 20 80 00 E0 60 3E 70 E8 7B 00 28 E6 D1 01 20 38 70 E3 E7 00 40 02 40 04 00 00 10 00 20 00 A0 FF FF FE FF 00 00 00 10 10 E0 00 E0 20 ED 00 E0 1C 80 04 40 14 82 04 40 00 E1 00 E0 01 00 00 A0 49 01 40 18 83 54 70 47 10 B5 32 4C 20 00 00 F0 BF F8 E1 21 49 02 20 00 00 F0 C7 F8 03 20 E0 60 81 20 A0 60 80 20 20 63 10 BD 00 00 03 28 00 DB 70 47 80 B5 01 23 4B 40 2D A1 0A 5C 2B A1 09 5C A0 20 00 06 FF F7 DC FF 01 BD 00 00 03 28 00 DB 70 47 10 B5 A0 21 09 06 24 A2 12 5C 92 00 89 18 8C 22 92 01 01 23 00 BF 21 A4 20 5C 83 40 8B 50 10 BD 00 00 F8 B5 FF F7 C7 FF A0 25 2D 06 28 00 00 F0 B6 F8 00 24 00 BF 18 A6 31 5D 88 00 28 18 80 22 92 01 80 18 00 BF 15 A2 12 5D 03 68 01 27 97 40 1F 43 07 60 01 23 28 00 FF F7 A9 FF 64 1C 03 2C EA DB F1 BD 00 00 80 B5 07 48 01 68 80 22 52 02 0A 43 02 60 19 22 0A A1 04 48 00 F0 98 F8 01 BD 00 00 00 80 00 40 80 80 04 40 00 40 04 40 80 B5 FF F7 E9 FF 00 F0 B1 F8 01 BD 02 02 02 00 11 10 12 00 00 03 81 00 00 04 81 00 00 05 81 00 00 08 81 00 00 09 81 00 00 0B 02 00 00 0C 02 00 00 0D 02 00 00 0E 02 00 00 12 81 00 00 13 81 00 00 17 01 00 01 09 01 00 01 0B 81 00 01 0E 81 00 01 14 82 00 01 15 82 00 01 16 81 00 01 17 82 00 01 1A 81 00 01 1B 81 00 01 1D 81 00 02 00 01 00 02 01 01 00 02 03 82 00 80 B5 00 F0 EF F8 01 49 08 60 01 BD 00 00 00 10 80 B5 03 4A 12 68 12 69 52 68 90 47 02 BD 00 00 F8 1F FF 1F 03 48 01 68 80 22 D2 05 0A 43 02 60 70 47 00 00 80 80 04 40 15 49 01 22 8A 61 0A 68 80 23 5B 01 13 43 0B 60 07 21 81 60 10 21 81 62 70 47 70 B5 04 00 0D 00 01 20 0E 49 08 60 00 F0 8F F8 06 00 29 01 FF F7 D3 FF 01 00 E0 68 80 22 02 43 E2 60 C8 B2 20 60 08 04 00 0E 60 60 E0 68 80 22 90 43 E0 60 30 00 FF F7 C2 FF 70 BD 00 00 80 80 04 40 98 80 04 40 02 48 01 68 40 22 0A 43 02 60 70 47 80 80 04 40 00 2A 00 D1 70 47 30 B4 0C 68 23 0C 25 0A E4 B2 00 2C 12 D0 02 2C 01 D0 0A D3 11 E0 ED B2 AC 00 04 19 02 2D 01 DB F4 25 00 E0 F0 25 63 51 07 E0 2D 06 AC 0D 04 19 23 66 02 E0 2D 06 AC 0D 03 51 09 1D 52 1E E0 D1 30 BC 70 47 FE E7 38 B5 20 20 00 F0 E8 F8 00 20 00 90 11 48 02 E0 00 99 49 1C 00 91 00 99 81 42 F9 DB 01 20 00 F0 1F F8 0D 48 01 68 01 24 03 22 91 43 21 43 01 60 80 20 00 F0 C7 F8 09 4D 23 20 28 60 80 20 00 F0 CB F8 68 68 C0 07 FC D5 2C 67 03 20 00 F0 10 F8 31 BD 00 00 C4 09 00 00 10 C0 03 40 08 80 04 40 42 49 FF E7 08 60 00 20 48 60 01 20 48 60 70 47 3F 49 F7 E7 43 A0 CA 05 12 0F 92 00 80 58 C9 06 C9 0E 49 1C 49 00 FF F7 49 FF 00 BD 00 B5 00 20 3B 49 03 22 8B 6E 13 40 11 D0 02 2B 11 D0 02 D3 03 2B 10 D0 00 BD 89 6B 0A 40 08 D0 01 2A 03 D0 03 2A 1A D1 31 48 00 E0 2F 48 00 68 00 BD 2D 48 00 BD C9 69 D6 E7 8B 6B 1A 40 08 D0 01 2A 03 D0 03 2A 05 D1 29 48 00 E0 27 48 00 68 00 E0 25 48 09 68 C9 06 C9 0E 49 1C 48 43 00 BD 00 00 00 00 10 B5 00 20 22 4C 03 21 A2 6E 0A 40 30 D0 02 2A 15 D0 21 D3 03 2A 2C D1 A2 6B 11 40 08 D0 01 29 03 D0 03 29 05 D1 19 48 00 E0 17 48 00 68 00 E0 14 48 21 68 C9 06 C9 0E 49 1C 48 43 19 E0 E1 69 14 A0 CA 05 12 0F 92 00 80 58 C9 06 C9 0E 49 1C 49 00 FF F7 EB FE 0C E0 A2 6B 11 40 08 D0 01 29 03 D0 03 29 05 D1 09 48 00 E0 07 48 00 68 00 E0 04 48 21 6F FF F7 DA FE 10 BD 00 00 40 80 04 40 70 80 04 40 00 1B B7 00 D0 09 00 00 D4 09 00 00 08 80 04 40 00 00 00 00 C0 27 09 00 90 05 10 00 C0 5C 15 00 F0 B3 1A 00 20 0B 20 00 00 9F 24 00 E0 32 29 00 C0 C6 2D 00 50 97 31 00 E0 67 35 00 70 38 39 00 00 09 3D 00 40 16 40 00 80 23 43 00 C0 30 46 00 0B 49 0A 68 10 43 09 4A 02 40 C8 20 00 02 10 43 08 60 70 47 06 49 0A 68 82 43 04 48 10 40 C8 22 12 02 02 43 0A 60 70 47 00 00 00 00 FF 25 00 00 38 82 04 40 70 B4 01 21 00 22 13 E0 04 68 00 1D 0C 42 02 D0 4D 46 6D 1E 64 19 22 60 24 1D 1B 1F 04 2B FA D2 25 00 9E 07 01 D5 22 80 AD 1C 0B 40 00 D0 2A 70 03 68 00 1D 00 2B E7 D1 70 BC 70 47 10 B5 07 49 79 44 18 31 06 4C 7C 44 16 34 04 E0 08 1D 0A 68 89 18 88 47 01 00 A1 42 F8 D1 10 BD 08 00 00 00 14 00 00 00 9D FF FF FF 08 00 00 00 00 00 00 10 00 00 00 00 00 F0 0B F8 00 28 01 D0 FF F7 DE FF 00 20 00 BF 00 BF FF F7 0C FD 00 F0 02 F8 01 20 70 47 80 B5 00 F0 02 F8 01 BD FE E7 07 46 38 46 00 F0 02 F8 FB E7 FE E7 20 21 09 03 26 31 18 20 AB BE F9 E7 01 48 80 47 01 48 00 47 D9 09 00 00 C5 09 00 00 00 BF 00 BF 00 BF 00 BF FF F7 D2 FF 00 1B B7 00 00 80 00 00 80 B5 FF F7 DF FD 01 BD FE E7 FE E7 FE E7                                                    Table 1 Drag and drop the binary file Running the secondary bootloader, and connect a USB cable between the PC and the J3, see Fig 6; Fig 6 Drag and drop the binary file to the driver, see Fig 7;    Fig 7 Review the values of the user application in the relative area , see Fig 8; Fig 8
View full article
Since the mbed Ethernet library and interface for FRDM-K64 have not yet been fully tested, instead of using mbed we will use one of the latest demo codes from MQX specifically developed for the FRDM-K64 platform. Before starting please make sure you have the following files and software installed in your computer: CodeWarrior 10.6 (professional or evaluation edition) MQX 4.1 for FRDM-K64 (it is not necessary to install full MQX 4.1) JLink_OpenSDA_V2.bin (this is the debugger application) * If you don't have a valid license, you can find a temporary license below, it will only be valid until 7/30/2014 and it will only be available online until 7/05/2014. Building the project The first step to use an MQX project is to compile the target/IDE libraries for the specific platform: 1. Open CodeWarrior and drag the file from the following path C:\Freescale\Freescale_MQX_4_1_FRDMK64F\build\frdmk64f\cw10gcc onto your project area: This will load all the necessary libraries to build the project, once they are loaded build them it is necessary to modify a couple of paths on the BSP: 2. Right click on the BSP project and then click on properties 3. Once the properties are displayed, expand the C/C++ Build option, click on settings, on the right pane expand the ARM Ltd Windows GCC Assembler and select the directories folder, this will display all the libraries paths the compiler is using 4. Double click on the "C\Freescale\CW MCU v10.6\MCU\ProcessorExpert\lib\Kinetis\pdd_100331\inc" path to modify it, once the editor window is open, change the path from "pdd_100331" to "pdd" 5. Repeat steps 2 and 3 for the ARM Ltd Windows GCC Compiler 6. Now you can build the libraries, build them one at a time by right clicking on the library and selecting build project, build them in the following order, it is imperative you do it in that order. BSP PSP MFS RTCS SHELL USBD USBH 7. Once all the libraries are built, import the web hvac demo, do it by dragging the .project file to your project area; the project is located in the following directory:                     C:\Freescale\Freescale_MQX_4_1_FRDMK64F\demo\web_hvac\build\cw10gcc\web_hvac_frdmk64f 8. Once the project is loaded, build it by right clicking on the project folder and select Build project Debugging the project To debug the project it is necessary to update the FRDM-K64 debugging application: Press the reset button on the board and connect the USB cable Once the board enumerates as "BOOTLOADER" copy the JLink_OpenSDA_vs.bin file to the unit Disconnect and reconnect the board On CodeWarrior (having previously compiled the libraries and project) click on debug configurations 5. Select the connection and click on debug 6. Open HVAC.h and change the IP Address to 192.168.1.202 Now the demo code has been downloaded to the platform you will need the following to access all the demo features: Router Ethernet Cable Serial Terminal The code enables a shell access through the serial terminal, it also provides web server access with a series of options to simulate an Heating Air Conditioning Ventilation System, the system was implemented using MQX and a series of tasks, for more details on how the task are created, the information regarding how to modify the code please check the attached document: Freescale MQX RTOS Example guide.
View full article
When using ADCs it is not enough to just configure the module, add a clock signal, apply the Nyquist criteria and hope for the best, because normally that is just not enough. Even if we use the best software configuration, sampling rate, conversion time, etc; we might end up with noisy conversions, and worst of all a low ENOB figure which sums up in a lousy, low resolution ADC application. To complement the software end you need to follow some basic hardware design rules, some of them might seem logical, other might even weird or excessive however they are the key to a successful conversion, I took the time to compile a short list of effective design best practices trying to cover the basics of ADC design. If you think I missed something feel free to comment and ask for more information. Ground Isolation Because ground is the power return for all digital circuits and analog circuits, one of the most basic design philosophies is to isolate digital and analog grounds. If the grounds are not isolated, the return from the analog circuitry will flow through the analog ground impedance and the digital ground current will flow through the analog ground, usually the digital ground current is typically much greater than the analog ground current.  As the frequency of digital circuits increases, the noise generated on the ground increases dramatically. CMOS logic families are of the saturating type; this means the logic transitions cause large transient currents on the power supply and ground. CMOS outputs connect the power to ground through a low impedance channel during the logic transitions. Digital logic waveforms are rectangular waves which imply many higher frequency harmonic components are induced by high speed transmission lines and clock signals.                              Figure 1: Typical mixed signal circuit grounding                              Figure 2: Isolated mixed signal circuit grounding Inductive decoupling Another potential problem is the coupling of signal from one circuit to another via mutual inductance and it does not matter if you think the signals are too weak to have a real effect, the amount of coupling will depend on the strength of the interference, the mutual inductance, the area enclosed by the signal loop (which is basically an antenna), and the frequency. It will also depend primarily on the physical proximity of the loops, as well as the permeability of the material. This inductive coupling is also known as crosstalk in data lines.                               Figure 3: Coupling induced noise It may seem logical to use a single trace as the return path for the two sources (dotted lines). However, this would cause the return currents for both signals to flow through the same impedance, in addition; it will maximize the area of the interference loops and increase the mutual inductance by moving the loops close together. This will increase the mutual noise inductance and the coupling between the circuits. Routing the traces in the manner shown below minimizes the area enclosed by the loops and separates the return paths, thus separating the circuits and, in turn, minimizing the mutual noise inductance.                               Figure 4: Inductance decoupling layout Power supply decoupling The idea after power decoupling is to create a low noise environment for the analog circuitry to operate. In any given circuit the power supply pin is really in series with the output, therefore, any high frequency energy on the power line will couple to the output directly, which makes it necessary to keep this high frequency energy from entering the analog circuitry. This is done by using a small capacitor to short the high frequency signals away from the chip to the circuit’s ground line. A disadvantage of high frequency decoupling is it makes a circuit more prone to low frequency noise however it is easily solved by adding a larger capacitor. Optimal power supply decoupling A large electrolytic capacitor (10 μF – 100 μF) no more than 2 in. away from the chip. A small capacitor (0.01 μF – 0.1 μF) as close to the power pins of the chip as possible. A small ferrite bead in series with the supply pin (Optional).                               Figure 5: Power supply decoupling layout Treat signal lines as transmission lines Although signal coupling can be minimized it cannot be avoided, the best approach to effectively counteract its effects on signal lines is to channel it into a conductor of our choice, in this case the circuit’s ground is the best choice to channel the effects of inductive coupling; we can accomplish this by routing ground lines along signal lines as close as manufacturing capabilities allow. An very effective way to accomplish this is routing signals in triplets, these works for both digital and analog signals.The advantages of doing so are an improved immunity not only to inductive coupling but also immunity to external noise. Optimal routing: Routing in “triplets” (S-G-S) provide good signal coupling with relatively low impact on routing density Ground trace needs to be connected to the ground pins on the source and destination devices for the signal traces Spacing should be as close as manufacturing will allow                               Figure 6: Transmission line routing Signal acquisition circuit To improve noise immunity an external RC acquisition circuit can be added to the ADC input, it consists of a resistor in series with the ADC input and a capacitor going from the input to the circuit’s ground as the figure below shows:                                                             Figure 7: ADC with an external acquisition circuit The external RC circuit values depend on the internal characteristics and configuration of the ADC you use, such as the availability of an internal gain amplifier or the ADC’s architecture; the equation and circuit shown here represents a simplified form of ADC used in Freescale devices. The equivalent sampling resistance RSH is represented by total serial resistance connected between sampling capacitance and analog input pin (sampling switch, multiplexor switches etc.). The sampling capacitance CSH is represented by total parallel capacitance. For example in a case of Freescale SAR ADC equivalent sampling capacitance contains bank of capacitances. The equation shown how to calculate the value of the input resistor based on the values of both the input and sample and hold circuit. It must be noted the mentioned figures could have an alternate designation in any given datasheet; the ones mentioned here are specific to Kinetis devices: TAQ=      Acquisition time (.5/ADC clock) CIN=       Input capacitance (33pF min) CSH=      Sample & Hold circuit capacitance ( CDAIN in datasheet) VIN=       Input voltage level VCSH0= Initial voltage across S&H circuit (0V) VSFR=    Full scale voltage (VDDA) N=           bit resolution Note:  Special care must be taken when performing the calculation since a deviation from the correct values will result in a significant conversion error due to signal distortion.
View full article
You can put the code directory in the SDK_2.6.0_FRDM-K64F\boards\frdmk64f to use. 1、Introduction As is known to all, we use debugger to download the program or debug the device. FRDMK64 have the opsenSDA interface on the board, so wo do not need other’s debugger. But if we want to design a board without debugger but can download the program, we can use the bootloader. The bootloader is a small program designed to update the program with the interface such as UART,I2C,SPI and so on. This document will describe a simple bootloader based on the FRDMK64F.The board uses SD card to update the application. User can put the binary file into the card. When the card insert to the board ,the board will update the application automatically. The bootloader code and application code are all provided so that you can test it on your own board.   2、Bootloader’s implementation   The schematic for SD card is shown below. The board uses SDHC module to communicate with SD card.                                                  Figure 1.Schematic for SD card   We use the 2.6.0 version of FRDM-K64F’s SDK.You can download the SDK in our website. The link is “mcuxpresso.nxp.com”. The bootloader uses SDHC and fafts file system. So we should add files to support it.                   Figure 2.The support file   In main code, the program will wait until the card has inserted. Then it will find the file named “a000.bin” in sd card to update the application. If the file do not exist, the board will directly execute the application. If there is no application, the program will end. The following code shows how the program wait for inserting sd card. It will also check if the address has the application’s address.                      Figure 3.The code -- wait for inserting card   The following code shows how the program opens the binary file. If sd card doesn’t have the file, the program will go to the application. Figure 4.Open the binary file   If the program opens the file normally, the update will begin. It will erase 200k’s space from 0xa000. You can adjust it according to your project. Now I will explain update’s method in detail. Our data is written to the buffer called “rBUff”. The buffer size is 4K. Before write data to it, it is cleared.  Please note that when we erase or program the flash, we should disable all interrupts and when the operations finish we should enable the interrupts.  The file size will decide which way to write the data to flash.  1、If the size < 4k ,we just read the file’s data to buffer and judge if its size aligned with 8 byte. If not , we increase the size of “readSize” to read more data in our data buffer called “rBuffer”. The more data we read is just 0.    2、If the size > 4K, we use “remainSize” to record how much data is left. We read 4k each time until its size is smaller than 4k and then repeat step 1. When finish the operation at a  time, we should clear the buffer and increase the sector numer to prepare the next transmission. Figure 5.Write flash operation code   The way to clear the space is shown in the figure. It will initialize the flash and erase the given size from the given address.  “SectorNum” is used to show which sector to erase. Figure 6.Erase operation code   The following figure shows how to write the data to flash.              Figure 7.Program operation code    Before we go to the application, we should modify the configuration we did in the bootloader.     Close the systick, clear its value.     Set the VTOR to default value.     Our bootloader runs in PEE mode. So we should change it to FEI mode.     Disable the all pins. You should disable the global interrupt when run these codes. And don’t forget to enable the global interrupt. Figure 8.Deinitalization code   Then we can go to the application. Figure 9.Go to Application   3、Memory relocation The FRDMK64 has the 1M flash, from 0x00000000 to 0x00100000.As shown in figure 10,we use the 0xa000 as the application’s start address.            Figure 10.The memory map   Now, I will show you how to modify the link file for user application in different IDE. In IAR                                    Figure 11.IAR’s ICF In MDK Figure 12.MDK’s SCF   In MCUXpresso Figure 13.MCUXpresso’s flash configuration 4、Run the demo 1) Download the bootloader first. 2) Prepare a user application program. We use the “led blinky” as an example. 3) Modify the Link file. 4) Generate the binary file with your IDE, please name it as “a000.bin”. 5) Put it into the sd card like figure 5. Figure 14.SD card’s content        6) Insert the card. And power on. Wait for a moment, the application will execute automatically. 5、Reference 1) Kinetis MCU的bootloader解决方案 2) KEA128_can_bootloader
View full article
Hey there Kinetis lovers!  We in the Systems Engineering team for Kinetis Microcontrollers see all kinds of situations that customers get into, and none can be particularly troubling like how the reset pin is handled.  The purpose of this document is to provide a list of Frequency Asked Questions (FAQ) that we get here in the Kinetis Systems Engineering department.  This is intended to be a living list and as such, may in no way be complete.  However we hope that you will find the below questions and answers useful.   Q:  Do I need to connect the reset signal to be able to debug a Kinetis device?   This is a commonly asked question. Strictly speaking, you do not need to connect the device reset line of a Kinetis device to the debug connector to be able to debug. The debug port MDM-AP register allows the processor to be held in reset by means of setting the System Reset Request bit using just the SWD_CLK and SWD_DIO lines.   However, before deciding to omit the reset line from your debug connector you should give some careful thought to how this may impact the ability to program and debug the device in certain scenarios. Does the debugger/flash programmer or external debug pod require the reset pin? It may be that the specific tool you are using only supports resetting the device by means of the reset line and does not offer the ability to reset the device by means of the MDM-AP. Have you changed the default function of the debug signals? You may need to use the SWD_CLK and/or the SWD_DIO signals for some other function in your application. This is especially true in low pin count packages. Once the function is changed (by means of the PORTx_PCRy registers) you will no longer have access to the MDM-AP via those signals. If you do not have access to the reset signal then you have no way of preventing the core from executing the code that will disable the SWD function of the pins. So you will not be able to re-program the device. In order to prevent this type of situation you need to either: Setup your code to change the function of the SWD pins several seconds after reset is released so that the debugger can halt the core before this happens. Put some kind of “backdoor” mechanism in your code that does not re-program the SWD function, or re-enables the SWD function, on these pins. For example, a specific character sequence sent via a UART or SPI interface.   Some Kinetis devices allow the reset function of the reset pin to be disabled. In this case you can only use the SWD signals as a means of resetting the device via the MDM-AP. If you change the SWD pin function in addition to disabling the reset pin then you must provide a backdoor means of re-enabling the SWD function if you want to be able to reprogram the device.
View full article
Here you will find both the code and project files for the ADC project. This project configures the ADC to perform single conversions, by default this is performed using a 16 bit configuration. The code uses ADC0, channel 12, once the conversion is finished it is displayed at the serial terminal. Code: #include "mbed.h" AnalogIn AnIn(A0); DigitalOut led(LED1); Serial pc(USBTX,USBRX); float x; int main() {     pc.printf(" ADC demo code\r\n");     while (1)     {     x=AnIn.read();     pc.printf("ADC0_Ch12=(%d)\r\n", x);     wait(.2);     } }
View full article
Hi Community members! Here you can find the source code of the MSD Host Bootloader implemented on the AN4368 document using the TWR-K70F120M and CodeWarrior 10.6 and a document that describes the migration process of the original source code for the TWR-K60N512 to a TWR-K70F120M and the steps to use the application. Attached you will find a image.s19 file created to be used with the bootloader application as an example. :smileyinfo: This document and code are intended to demonstrate the use of the AN4368 source code on a 120 MHz device and CodeWarrior 10.6 but is not replacing the work done on the application note. I hope this can be helpful for you! Best Regards, Adrian :smileyplus: If it was useful for you do not forget to click on the Like button. It would be nice!
View full article
     我想“超频”这个词估计大家都不会陌生,很多玩计算机的都会尝试去把自己电脑的CPU超频玩一些高端大型游戏(咳咳,当然玩的high的时候别忘了小心你的主板别烧了),而对我们这些搞嵌入式的人们来说,估计就只能用这样的情怀去折磨MCU了(当然前提得是有PLL或者FLL的MCU)。      在超频之前首先需要澄清几个概念,我们通常所说的主频一般是指内核时钟或者系统时钟(即core_clk或system_clk)。而对K60来说,其内部还有总线时钟(Bus_clk)、外部总线时钟(FlexBus_clk)、flash时钟(Flash_clk),而这几个时钟互相关联且每个都是有其频率限制的(如下图1所示),所以当我们要超频内核时钟的时候还不得不考虑其他时钟承受极限(姑且用这个词吧)。在我们用MCG模块内部的PLL将输入时钟超频到200MHz作为MCGOUTCLK输出的时候还需要一道关卡(如下图2),也就是说虽然这几个时钟属于同宗(都来自MCGOUTCLK),但是也可以通过不同的分频器(OUTDIV[1:4])约束不同的时钟范围,这里想起一个形象的例子。MCGOUTCLK就类似以前的官家大老爷,娶了四房姨太太(OUTDIV[1:4]),分别生了四个少爷(即core_clk、Bus_clk、FlexBus_clk和Flash_clk),每个少爷都是老爷的儿子,不过在家中地位却是由姨太太的排序决定的,其中大房的大少爷(core_clk)地位最高(频率范围最大),四房的小少爷(flash_clk)地位最低(频率范围最小),不过他们的地位最高也不会超过老爷(其他clk<=MCGOUTCLK),呵呵,有点意思~ 图1 图2      经过上面的分析之后,就可以开始着手超频了。经过验证,其实系统频率超不上去就是“小少爷”(flash_clk)拖了后腿,当我们将MCGOUTCLK超到200MHz的时候,OUTDIV1的分频可以设置为1分频,保证内核频率为200MHz,但却要同时保证其他几个时钟不要超过太多,尤其是Flash_clk的限制要严格(建议不要超过30MHz,小少爷有些“娇气”),因为flash_clk过高就代表取指令的频率过高,指令出错就会造成系统程序跑飞。     说到这里,可能有些人会质疑,把主频超的那么高,但取指令的速度上不去有个啥用,岂不是颇有些大马拉小车的感觉吗,其实不然,这里我说两点。一个是通过RAM调试或者将函数声明成RAM执行函数的时候是可以加快执行速度的,另一个就是当做一些数学运算的时候作用就很明显了,因为一般可能会单纯用到CPU内部的ALU和寄存器组,后者数据访问多一些(注意Cortex-M4是哈佛结构,数据与指令总线独立的),自然其运算速度就上去了,所以还是好处多多的。      当然飞思卡尔本身是不建议超频的,数据手册上给出的极限值都是在保证系统可靠性和稳定性的前提下测试出来的,再往上就不敢保证了(跟你的硬件电路设计能力有一定关系),正所谓“超频有风险,用时需谨慎啊”,呵呵,所以我们大多数的应用还是老老实实的按照“规矩”来吧。不过这里需要提的一点是,每家厂商一般会为超频留有余地(为了满足一些客户的超频需要,哎,不容易啊),至于这个余地是多少,不同的半导体厂商也会有不同的标准。对我来说,记得那是2008年的第一场雪,比往年来的稍晚了些…(没收住,开始整词儿了,呵呵),那一年我第一次接触飞思卡尔的9S12 16位的单片机(MC9S12DG128,哎,搞过智能车的都懂的),额定主频是25MHz,我把它超到40MHz,后来又换成了MC9S12XS128,额定主频是40MHz,我又把它超到80MHz(有点超频强迫症了,呵呵),一直到如今的ARM K60,额定主频为100MHz(VLQ100),所以。。。咳咳。。。很自然的我就把它超到200MHz,再往上我就没有测试了,因为基本也用不到那么高的频率,还是要掌握好这个“度”的,想过把超频的瘾的可以试试看,呵呵~
View full article
Recently I did a porting based on AN4370SW for a customer to support TWR-K20D72M, and with some modification in source code, header file and link file as well, it works well as expected. The following simple describes what I have done: 1.Copy the project file folder for K20D50M "AN4370SW\Source\Device\app\dfu_bootloader\iar_ew\kinetis_k20" and rename is as "kinetis_k20d70m" 2.Change the target settings as well as the flash loader. 3. Replace the header file for K20D50M and include it in derivative.h. The header file for K20D72M can be found from KINETIS_72MHz_SRC(http://cache.freescale.com/files/32bit/software/KINETIS_72MHz_SRC.zip?fpsp=1&WT_TYPE=Lab%20and%20Test%20Software&WT_VENDOR=FREESCALE&WT_FILE_FORMAT=zip&WT_ASSET=Downloads&sr=9) 4.Modify the interrupt table in cstartup_M.s, which is more likely a K60's vertor table. 5.Search the code related with the macro "MCU_MK20D5", and add similar code snippet for K20D72M , You may easily find them by search the keyword "MCU_MK20D7". That code parts include initialization for MCG, and PIT0 and USB interrupt enablements, some definition in bootloader.h . 6. Copy the link file from K20D50M, and modify the PFLASH size,SRAM size and DFLASH size as shown below: Perform MassErase before programming . and then you may press the SW1 on TWR-K20D72M to select which mode to enter after download the application firmware: pressing SW1 to enter bootloader mode and releasing it to enter application mode. 7. Build image for this DFU bootloader. Actually the bareboard projects in KINETIS_72MHz_SRC can be used for that purpose, and only link file needs some modification to put the image starting from 0xA000, since exception table redirection has already been done in these projects. after that, user needs change some settings in the CW projects to use the new link file: and generate S19 file as the output as well as the map file: after compiling , you will have a xxx.afx.s19 file, but that is not the final format, we still need to transform it to bin format, and it can be done by a small tool in "C:\Program Files\Freescale\CW MCU v10.3\MCU\prog" There are some settings for this tool to transform the S19 file, by clicking Burner->Burner Dialog, you will see some option views, please set them as below: Referring to the above figure, maybe you would wonder how to set up the Origin and Length field, actually Origin is the value where the image starts from just as the link file specified , and Length is calculated by the results from the map file. Please refer to the following figure for details. 0x3550 = 0x1c90 + 0x18c0. I also attached the burner's configuration file and image link file as well as the image for reference. Please copy the link file in "KINETIS_72MHz_SRC\build\cw\linker_files". Please kindly refer to the attachment for more details. Hope that helps, B.R Kan
View full article
Hello Kinetis friends! The launch of new Kinetis devices and development tools called "Kinetis K2" brought some new K22_120 MHz devices to the K22 family portfolio. :smileyinfo: Please notice the name "Kinetis K2" only refers to the Kinetis generation, but it is not related to part number (e.g. K63/K64 are part of K2 generation). Previously existing Kinetis portfolio already had some K22_120 MHz devices, so this  caused confusion regarding the documentation, header files, features, development boards and others, because the part numbers are very similar. I created the next reference table outlining the existing K22_120 MHz parts with their corresponding files and boards. The last column is an overview of the features or peripherals that are either missing or added in each device. :smileyalert: IMPORTANT NOTES:           - I gathered and put together this information as reference, but it is not official. For the most accurate information please visit our webpage www.nxp.com.           - Header files MK22F12.h and MK22FA12.h apply for legacy K22_120 devices. However TWR-K21F120M(A) board has a K21_120 part, so use MK21F12.h or MK21FA12.h instead.      Colleague Carlos Chavez released an Engineering Bulletin (EB811) with good information related to this document:      http://cache.nxp.com/files/microcontrollers/doc/eng_bulletin/EB811.pdf Regards! Jorge Gonzalez
View full article
Overview          KBOOT v2.0 had been released in the Q2 of the 2016 and it has a lot of new features versus the previous version. For instance, the USB peripheral can work as Mass Storage Class device mode now, not just only supports the HID interface. And in following, USB MSD Bootloader implementation will be illustrated. Preparation FRDM-K64F board Fig1 FRDM-K64F KBOOT v2.0 downloading: KBOOT v2.0 IDE: IAR v7.50 Application demo: KSDK v2.0   Flash-resident bootloader           The K64_120 doesn’t contain the ROM-based bootloader, so the flash-resident bootloader need to be programmed in the K64 and the flash-resident bootloader can be used to download and program an initial application image into a blank area on the flash, and to later update the application.         I. Open the the bootloader project, for instance, using the IAR and select the freedom_bootloader demo         The Fig 2 illustrates the bootloader project for K64 which resides in ~\NXP_Kinetis_Bootloader_2_0_0\NXP_Kinetis_Bootloade r_2_0_0\targets\MK64F12. Fig 2      II. After compiles the demo, then clicks the  button to program the demo to the K64 Linker file modification       According to the freedom_bootloader demo, the vector table relocation address of the application demo has been adapted to the 0xa000 (Table 1), however the default start address of the application is 0x0000_0000. So it’s necessary to modify the linker file to fit the freedom_bootloader and the Table 2 illustrates what the modifications are.                                                     Table 1 // The bootloader will check this address for the application vector table upon startup. #if !defined(BL_APP_VECTOR_TABLE_ADDRESS) #define BL_APP_VECTOR_TABLE_ADDRESS 0xa000 #endif                                                   Table 2 define symbol __ram_vector_table_size__ = isdefinedsymbol(__ram_vector_table__) ? 0x00000400 : 0; define symbol __ram_vector_table_offset__ = isdefinedsymbol(__ram_vector_table__) ? 0x000003FF : 0; //define symbol m_interrupts_start       = 0x00000000; //define symbol m_interrupts_end         = 0x000003FF; define symbol m_interrupts_start       = 0x0000a000; define symbol m_interrupts_end         = 0x0000a3FF; //define symbol m_flash_config_start     = 0x00000400; //define symbol m_flash_config_end       = 0x0000040F; define symbol m_flash_config_start     = 0x0000a400; define symbol m_flash_config_end       = 0x0000a40F; //define symbol m_text_start             = 0x00000410; define symbol m_text_start             = 0x0000a410; define symbol m_text_end               = 0x000FFFFF; define symbol m_interrupts_ram_start   = 0x1FFF0000; define symbol m_interrupts_ram_end     = 0x1FFF0000 + __ram_vector_table_offset__; define symbol m_data_start             = m_interrupts_ram_start + __ram_vector_table_size__; define symbol m_data_end               = 0x1FFFFFFF; define symbol m_data_2_start           = 0x20000000; define symbol m_data_2_end             = 0x2002FFFF; /* Sizes */ if (isdefinedsymbol(__stack_size__)) {   define symbol __size_cstack__        = __stack_size__; } else {   define symbol __size_cstack__        = 0x0400; } if (isdefinedsymbol(__heap_size__)) {   define symbol __size_heap__          = __heap_size__; } else {   define symbol __size_heap__          = 0x0400; } define exported symbol __VECTOR_TABLE  = m_interrupts_start; define exported symbol __VECTOR_RAM    = isdefinedsymbol(__ram_vector_table__) ? m_interrupts_ram_start : m_interrupts_start; define exported symbol __RAM_VECTOR_TABLE_SIZE = __ram_vector_table_size__; define memory mem with size = 4G; define region m_flash_config_region = mem:[from m_flash_config_start to m_flash_config_end]; define region TEXT_region = mem:[from m_interrupts_start to m_interrupts_end]                           | mem:[from m_text_start to m_text_end]; define region DATA_region = mem:[from m_data_start to m_data_end]                           | mem:[from m_data_2_start to m_data_2_end-__size_cstack__]; define region CSTACK_region = mem:[from m_data_2_end-__size_cstack__+1 to m_data_2_end]; define region m_interrupts_ram_region = mem:[from m_interrupts_ram_start to m_interrupts_ram_end]; define block CSTACK    with alignment = 8, size = __size_cstack__   { }; define block HEAP      with alignment = 8, size = __size_heap__     { }; define block RW        { readwrite }; define block ZI        { zi }; initialize by copy { readwrite, section .textrw }; do not initialize  { section .noinit }; place at address mem: m_interrupts_start    { readonly section .intvec }; place in m_flash_config_region              { section FlashConfig }; place in TEXT_region                        { readonly }; place in DATA_region                        { block RW }; place in DATA_region                        { block ZI }; place in DATA_region                        { last block HEAP }; place in CSTACK_region                      { block CSTACK }; place in m_interrupts_ram_region            { section m_interrupts_ram }; SB file generation     I. Brief introduction of SB file         The Kinetis bootloader supports loading of the SB files. The SB file is a Freescale-defined boot file format designed to ease the boot process. The file is generated using the Freescale elftosb tool. The format supports loading of elf or srec files in a controlled manner, using boot commands such as load, jump, fill, erase, and so on. The boot commands are prescribed in the input command file (boot descriptor .bd) to the elftosb tool. The format also supports encryption of the boot image using AES-128 input key.          And right now, the USB MSD bootloader only support SB file drag and drop.    II. Generate the BIN file         After open the hello_world demo in the IAR, using project options dialog select the "Output Converter" and change the output format to "binary" for outputting .BIN format image (Fig 3). Next, build the application demo, then the .BIN file will be generated after the building completes. Fig 3      III. Create BD file There is a template BD file which resides in the ~\NXP_Kinetis_Bootloader_2_0_0\NXP_Kinetis_Bootloader_2_0_0\apps\led_demo\src. Next, adapt the BD file by referring to the Kinetis Elftosb User's Guide, the following table shows the BD file content.                                                    Table 3 sources {         # BIN File path         myBINFile = "hello_world.bin"; } section (0) {         #1. Erase the internal flash         erase 0x0000a000..0x0010000;         #2. Load BIN File to internal flash         load myBINFile > 0xa000;         #3. Reset target.         reset; }      IV.  SB file generation          After creating the BD file shown in the following figure, copy the "hello_world.bin", elftosb.exe, and the BD file into the same directory. Then, open the window with command prompt and invoke elftosb such as “elftosb –V –c FRDM-K64F.bd –o image.sb”. The elftosb processes the FRDM-K64F.bd file and generates an image.sb file. Elftosb also outputs the commands list as shown in Fig 4. Fig 4     V. Application code updating       Plug a USB cable from the PC to the USB connector J26 to power the board , then keep holding the button SW2 down until press and release the Reset button SW1, it can force the K64_120 enter the BOOTLOADER mode. Next, plug another USB cable from the PC to the USB connector J22 (Fig 5), the FSL Loader will come out after completes the enumeration and it will appear as a removable storage driver (Fig 6).  Copy & paste or drag & drop the image.sb to the FSL Loader drive to update the application code, and the Fig 7 illustrates the result of application code runs. Fig 5 Fig 6 Fig 7
View full article
The following document contains a list of documents , questions and discussions that are relevant in the community based on the amount of views they are receiving each month. If you are having a problem, doubt or getting started in Kinetis processors or MCUXpresso, you should check the following links to see if your doubt have been already solved in the following documents and discussions. MCUXpresso MCUXpresso Supported Devices Table FAQ: MCUXpresso Software and Tools  Getting Started with MCUXpresso and FRDM-K64F  Generating a downloadable MCUXpresso SDK v.2 package  Quick Start Guide – Using MCUXpresso SDK with PINs&amp;CLOCKs Config Tools  Moving to MCUXpresso IDE from Kinetis Design Studio Kinetis Microcontrollers Guides and examples Using RTC module on FRDM-KL25Z  Baremetal code examples using FRDM-K64F Using IAR EWARM to program flash configuration field Understanding FlexIO  Kinetis K80 FAQ How To: Secure e-mail client (SMTP + SSL) with KSDK1.3 + WolfSSL for FRDM-K64F  Kinetis Bootloader to Update Multiple Devices in a Network - for Cortex-M0+  PIT- ADC- DMA Example for FRDM-KL25z, FRDM-K64F, TWR-K60D100 and TWR-K70  USB tethering host (RNDIS protocol) implementation for Kinetis - How to use your cellphone to provide internet connectivity for your Freedom Board using KSDK Write / read the internal flash Tracking down Hard Faults  How to create chain of pbuf's to be sent? Send data using UDP.  Kinetis Boot Loader for SREC UART, SD Card and USB-MSD loading  USB VID/PID numbers for small manufacturers and such like  Open SDA and FreeMaster OpenSDAv2  Freedom OpenSDA Firmware Issues Reported on Windows 10 Let´s start with FreeMASTER!  The Kinetis Design Studio IDE (KDS IDE) is no longer being actively developed and is not recommended for new designs. The MCUXpresso IDE has now replaced the Kinetis Design Studio IDE as the recommended software development toolchain for NXP’s Kinetis, LPC and i.MX RT Cortex-M based devices. However, this documents continue to receive considerable amount of views in 2019 which means it could be useful to some people. Kinetis Design Studio New Kinetis Design Studio v3.2.0 available Using Kinetis Design Studio v3.x with Kinetis SDK v2.0  GDB Debugging with Kinetis Design Studio  KDS Debug Configurations (OpenOCD, P&amp;E, Segger) How to use printf() to print string to Console and UART in KDS2.0  Kinetis Design Studio - enabling C++ in KSDK projects  Using MK20DX256xxx7 with KDS and KSDK  Kinetis SDK Kinetis SDK FAQ  Introducing Kinetis SDK v2  How to: install KSDK 2.0  Writing my first KSDK1.2 Application in KDS3.0 - Hello World and Toggle LED with GPIO Interrupt 
View full article