X-Git-Url: http://git.linex4red.de/pub/USBasp.git/blobdiff_plain/071e02c6b6b4837fa9cf0b6d4c749994e02638d7..059307d89cbdd7a45170566f469eb9e02c20b3e1:/LUFA/DriverStubs/Dataflash.h diff --git a/LUFA/DriverStubs/Dataflash.h b/LUFA/DriverStubs/Dataflash.h index d00d3ef6e..668dbad35 100644 --- a/LUFA/DriverStubs/Dataflash.h +++ b/LUFA/DriverStubs/Dataflash.h @@ -67,10 +67,10 @@ #define DATAFLASH_NO_CHIP DATAFLASH_CHIPCS_MASK /** Mask for the first dataflash chip selected. */ - #define DATAFLASH_CHIP1 // TODO: Replace with mask to select the first Dataflash chip + #define DATAFLASH_CHIP1 // TODO: Replace with mask to hold /CS of first Dataflash low, and all others high /** Mask for the second dataflash chip selected. */ - #define DATAFLASH_CHIP2 // TODO: Replace with mask to select the second Dataflash chip, if available + #define DATAFLASH_CHIP2 // TODO: Replace with mask to hold /CS of second Dataflash low, and all others high /** Internal main memory page size for the board's dataflash ICs. */ #define DATAFLASH_PAGE_SIZE // TODO: Replace with the page size for the Dataflash ICs @@ -79,6 +79,44 @@ #define DATAFLASH_PAGES // TODO: Replace with the total number of pages inside one of the Dataflash ICs /* Inline Functions: */ + /** Initializes the dataflash driver so that commands and data may be sent to an attached dataflash IC. + * The AVR's SPI driver MUST be initialized before any of the dataflash commands are used. + */ + static inline void Dataflash_Init(void) + { + DATAFLASH_CHIPCS_DDR |= DATAFLASH_CHIPCS_MASK; + DATAFLASH_CHIPCS_PORT |= DATAFLASH_CHIPCS_MASK; + } + + /** Determines the currently selected dataflash chip. + * + * \return Mask of the currently selected Dataflash chip, either \ref DATAFLASH_NO_CHIP if no chip is selected + * or a DATAFLASH_CHIPn mask (where n is the chip number). + */ + static inline uint8_t Dataflash_GetSelectedChip(void) ATTR_ALWAYS_INLINE ATTR_WARN_UNUSED_RESULT; + static inline uint8_t Dataflash_GetSelectedChip(void) + { + return (DATAFLASH_CHIPCS_PORT & DATAFLASH_CHIPCS_MASK); + } + + /** Selects the given dataflash chip. + * + * \param[in] ChipMask Mask of the Dataflash IC to select, in the form of DATAFLASH_CHIPn mask (where n is + * the chip number). + */ + static inline void Dataflash_SelectChip(const uint8_t ChipMask) ATTR_ALWAYS_INLINE; + static inline void Dataflash_SelectChip(const uint8_t ChipMask) + { + DATAFLASH_CHIPCS_PORT = ((DATAFLASH_CHIPCS_PORT & ~DATAFLASH_CHIPCS_MASK) | ChipMask); + } + + /** Deselects the current dataflash chip, so that no dataflash is selected. */ + static inline void Dataflash_DeselectChip(void) ATTR_ALWAYS_INLINE; + static inline void Dataflash_DeselectChip(void) + { + Dataflash_SelectChip(DATAFLASH_NO_CHIP); + } + /** Selects a dataflash IC from the given page number, which should range from 0 to * ((DATAFLASH_PAGES * DATAFLASH_TOTALCHIPS) - 1). For boards containing only one * dataflash IC, this will select DATAFLASH_CHIP1. If the given page number is outside @@ -95,8 +133,36 @@ if (PageAddress >= (DATAFLASH_PAGES * DATAFLASH_TOTALCHIPS)) return; - // TODO: If more than one dataflash chip, select the correct chip from the page address here - Dataflash_SelectChip(DATAFLASH_CHIP1); + #if (DATAFLASH_TOTALCHIPS == 2) + if (PageAddress & 0x01) + Dataflash_SelectChip(DATAFLASH_CHIP2); + else + Dataflash_SelectChip(DATAFLASH_CHIP1); + #else + Dataflash_SelectChip(DATAFLASH_CHIP1); + #endif + } + + /** Toggles the select line of the currently selected dataflash IC, so that it is ready to receive + * a new command. + */ + static inline void Dataflash_ToggleSelectedChipCS(void) + { + uint8_t SelectedChipMask = Dataflash_GetSelectedChip(); + + Dataflash_DeselectChip(); + Dataflash_SelectChip(SelectedChipMask); + } + + /** Spin-loops while the currently selected dataflash is busy executing a command, such as a main + * memory page program or main memory to buffer transfer. + */ + static inline void Dataflash_WaitWhileBusy(void) + { + Dataflash_ToggleSelectedChipCS(); + Dataflash_SendByte(DF_CMD_GETSTATUS); + while (!(Dataflash_ReceiveByte() & DF_STATUS_READY)); + Dataflash_ToggleSelectedChipCS(); } /** Sends a set of page and buffer address bytes to the currently selected dataflash IC, for use with @@ -106,9 +172,11 @@ * \param[in] BufferByte Address within the dataflash's buffer */ static inline void Dataflash_SendAddressBytes(uint16_t PageAddress, const uint16_t BufferByte) - { - // TODO: If more than one dataflash chip, adjust absolute page address to be correct for the current chip, - // also the shifts may need to be altered to suit the dataflash model being used + { + #if (DATAFLASH_TOTALCHIPS == 2) + PageAddress >>= 1; + #endif + Dataflash_SendByte(PageAddress >> 5); Dataflash_SendByte((PageAddress << 3) | (BufferByte >> 8)); Dataflash_SendByte(BufferByte);