x

Dependents:   20180621_FT813

Committer:
JackB
Date:
Mon Jul 23 12:22:51 2018 +0000
Revision:
0:b4f61c49c866
SPIF

Who changed what in which revision?

UserRevisionLine numberNew contents of line
JackB 0:b4f61c49c866 1 /* mbed Microcontroller Library
JackB 0:b4f61c49c866 2 * Copyright (c) 2016 ARM Limited
JackB 0:b4f61c49c866 3 *
JackB 0:b4f61c49c866 4 * Licensed under the Apache License, Version 2.0 (the "License");
JackB 0:b4f61c49c866 5 * you may not use this file except in compliance with the License.
JackB 0:b4f61c49c866 6 * You may obtain a copy of the License at
JackB 0:b4f61c49c866 7 *
JackB 0:b4f61c49c866 8 * http://www.apache.org/licenses/LICENSE-2.0
JackB 0:b4f61c49c866 9 *
JackB 0:b4f61c49c866 10 * Unless required by applicable law or agreed to in writing, software
JackB 0:b4f61c49c866 11 * distributed under the License is distributed on an "AS IS" BASIS,
JackB 0:b4f61c49c866 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
JackB 0:b4f61c49c866 13 * See the License for the specific language governing permissions and
JackB 0:b4f61c49c866 14 * limitations under the License.
JackB 0:b4f61c49c866 15 */
JackB 0:b4f61c49c866 16 #ifndef MBED_SPIF_BLOCK_DEVICE_H
JackB 0:b4f61c49c866 17 #define MBED_SPIF_BLOCK_DEVICE_H
JackB 0:b4f61c49c866 18
JackB 0:b4f61c49c866 19 #include <mbed.h>
JackB 0:b4f61c49c866 20 #include "BlockDevice.h"
JackB 0:b4f61c49c866 21
JackB 0:b4f61c49c866 22
JackB 0:b4f61c49c866 23 /** BlockDevice for SPI based flash devices
JackB 0:b4f61c49c866 24 * such as the MX25R or SST26F016B
JackB 0:b4f61c49c866 25 *
JackB 0:b4f61c49c866 26 * @code
JackB 0:b4f61c49c866 27 * // Here's an example using the MX25R SPI flash device on the K82F
JackB 0:b4f61c49c866 28 * #include "mbed.h"
JackB 0:b4f61c49c866 29 * #include "SPIFBlockDevice.h"
JackB 0:b4f61c49c866 30 *
JackB 0:b4f61c49c866 31 * // Create flash device on SPI bus with PTE5 as chip select
JackB 0:b4f61c49c866 32 * SPIFBlockDevice spif(PTE2, PTE4, PTE1, PTE5);
JackB 0:b4f61c49c866 33 *
JackB 0:b4f61c49c866 34 * int main() {
JackB 0:b4f61c49c866 35 * printf("spif test\n");
JackB 0:b4f61c49c866 36 *
JackB 0:b4f61c49c866 37 * // Initialize the SPI flash device and print the memory layout
JackB 0:b4f61c49c866 38 * spif.init();
JackB 0:b4f61c49c866 39 * printf("spif size: %llu\n", spif.size());
JackB 0:b4f61c49c866 40 * printf("spif read size: %llu\n", spif.get_read_size());
JackB 0:b4f61c49c866 41 * printf("spif program size: %llu\n", spif.get_program_size());
JackB 0:b4f61c49c866 42 * printf("spif erase size: %llu\n", spif.get_erase_size());
JackB 0:b4f61c49c866 43 *
JackB 0:b4f61c49c866 44 * // Write "Hello World!" to the first block
JackB 0:b4f61c49c866 45 * char *buffer = (char*)malloc(spif.get_erase_size());
JackB 0:b4f61c49c866 46 * sprintf(buffer, "Hello World!\n");
JackB 0:b4f61c49c866 47 * spif.erase(0, spif.get_erase_size());
JackB 0:b4f61c49c866 48 * spif.program(buffer, 0, spif.get_erase_size());
JackB 0:b4f61c49c866 49 *
JackB 0:b4f61c49c866 50 * // Read back what was stored
JackB 0:b4f61c49c866 51 * spif.read(buffer, 0, spif.get_erase_size());
JackB 0:b4f61c49c866 52 * printf("%s", buffer);
JackB 0:b4f61c49c866 53 *
JackB 0:b4f61c49c866 54 * // Deinitialize the device
JackB 0:b4f61c49c866 55 * spif.deinit();
JackB 0:b4f61c49c866 56 * }
JackB 0:b4f61c49c866 57 * @endcode
JackB 0:b4f61c49c866 58 */
JackB 0:b4f61c49c866 59 class SPIFBlockDevice : public BlockDevice {
JackB 0:b4f61c49c866 60 public:
JackB 0:b4f61c49c866 61 /** Creates a SPIFBlockDevice on a SPI bus specified by pins
JackB 0:b4f61c49c866 62 *
JackB 0:b4f61c49c866 63 * @param mosi SPI master out, slave in pin
JackB 0:b4f61c49c866 64 * @param miso SPI master in, slave out pin
JackB 0:b4f61c49c866 65 * @param sclk SPI clock pin
JackB 0:b4f61c49c866 66 * @param csel SPI chip select pin
JackB 0:b4f61c49c866 67 * @param freq Clock speed of the SPI bus (defaults to 40MHz)
JackB 0:b4f61c49c866 68 */
JackB 0:b4f61c49c866 69 SPIFBlockDevice(PinName mosi, PinName miso, PinName sclk, PinName csel, int freq=40000000);
JackB 0:b4f61c49c866 70
JackB 0:b4f61c49c866 71 /** Initialize a block device
JackB 0:b4f61c49c866 72 *
JackB 0:b4f61c49c866 73 * @return 0 on success or a negative error code on failure
JackB 0:b4f61c49c866 74 */
JackB 0:b4f61c49c866 75 virtual int init();
JackB 0:b4f61c49c866 76
JackB 0:b4f61c49c866 77 /** Deinitialize a block device
JackB 0:b4f61c49c866 78 *
JackB 0:b4f61c49c866 79 * @return 0 on success or a negative error code on failure
JackB 0:b4f61c49c866 80 */
JackB 0:b4f61c49c866 81 virtual int deinit();
JackB 0:b4f61c49c866 82
JackB 0:b4f61c49c866 83 /** Read blocks from a block device
JackB 0:b4f61c49c866 84 *
JackB 0:b4f61c49c866 85 * @param buffer Buffer to write blocks to
JackB 0:b4f61c49c866 86 * @param addr Address of block to begin reading from
JackB 0:b4f61c49c866 87 * @param size Size to read in bytes, must be a multiple of read block size
JackB 0:b4f61c49c866 88 * @return 0 on success, negative error code on failure
JackB 0:b4f61c49c866 89 */
JackB 0:b4f61c49c866 90 virtual int read(void *buffer, bd_addr_t addr, bd_size_t size);
JackB 0:b4f61c49c866 91
JackB 0:b4f61c49c866 92 /** Program blocks to a block device
JackB 0:b4f61c49c866 93 *
JackB 0:b4f61c49c866 94 * The blocks must have been erased prior to being programmed
JackB 0:b4f61c49c866 95 *
JackB 0:b4f61c49c866 96 * @param buffer Buffer of data to write to blocks
JackB 0:b4f61c49c866 97 * @param addr Address of block to begin writing to
JackB 0:b4f61c49c866 98 * @param size Size to write in bytes, must be a multiple of program block size
JackB 0:b4f61c49c866 99 * @return 0 on success, negative error code on failure
JackB 0:b4f61c49c866 100 */
JackB 0:b4f61c49c866 101 virtual int program(const void *buffer, bd_addr_t addr, bd_size_t size);
JackB 0:b4f61c49c866 102
JackB 0:b4f61c49c866 103 /** Erase blocks on a block device
JackB 0:b4f61c49c866 104 *
JackB 0:b4f61c49c866 105 * The state of an erased block is undefined until it has been programmed
JackB 0:b4f61c49c866 106 *
JackB 0:b4f61c49c866 107 * @param addr Address of block to begin erasing
JackB 0:b4f61c49c866 108 * @param size Size to erase in bytes, must be a multiple of erase block size
JackB 0:b4f61c49c866 109 * @return 0 on success, negative error code on failure
JackB 0:b4f61c49c866 110 */
JackB 0:b4f61c49c866 111 virtual int erase(bd_addr_t addr, bd_size_t size);
JackB 0:b4f61c49c866 112
JackB 0:b4f61c49c866 113 /** Get the size of a readable block
JackB 0:b4f61c49c866 114 *
JackB 0:b4f61c49c866 115 * @return Size of a readable block in bytes
JackB 0:b4f61c49c866 116 */
JackB 0:b4f61c49c866 117 virtual bd_size_t get_read_size() const;
JackB 0:b4f61c49c866 118
JackB 0:b4f61c49c866 119 /** Get the size of a programable block
JackB 0:b4f61c49c866 120 *
JackB 0:b4f61c49c866 121 * @return Size of a programable block in bytes
JackB 0:b4f61c49c866 122 * @note Must be a multiple of the read size
JackB 0:b4f61c49c866 123 */
JackB 0:b4f61c49c866 124 virtual bd_size_t get_program_size() const;
JackB 0:b4f61c49c866 125
JackB 0:b4f61c49c866 126 /** Get the size of a eraseable block
JackB 0:b4f61c49c866 127 *
JackB 0:b4f61c49c866 128 * @return Size of a eraseable block in bytes
JackB 0:b4f61c49c866 129 * @note Must be a multiple of the program size
JackB 0:b4f61c49c866 130 */
JackB 0:b4f61c49c866 131 virtual bd_size_t get_erase_size() const;
JackB 0:b4f61c49c866 132
JackB 0:b4f61c49c866 133 /** Get the value of storage when erased
JackB 0:b4f61c49c866 134 *
JackB 0:b4f61c49c866 135 * If get_erase_value returns a non-negative byte value, the underlying
JackB 0:b4f61c49c866 136 * storage is set to that value when erased, and storage containing
JackB 0:b4f61c49c866 137 * that value can be programmed without another erase.
JackB 0:b4f61c49c866 138 *
JackB 0:b4f61c49c866 139 * @return The value of storage when erased, or -1 if you can't
JackB 0:b4f61c49c866 140 * rely on the value of erased storage
JackB 0:b4f61c49c866 141 */
JackB 0:b4f61c49c866 142 virtual int get_erase_value() const;
JackB 0:b4f61c49c866 143
JackB 0:b4f61c49c866 144 /** Get the total size of the underlying device
JackB 0:b4f61c49c866 145 *
JackB 0:b4f61c49c866 146 * @return Size of the underlying device in bytes
JackB 0:b4f61c49c866 147 */
JackB 0:b4f61c49c866 148 virtual bd_size_t size() const;
JackB 0:b4f61c49c866 149
JackB 0:b4f61c49c866 150 private:
JackB 0:b4f61c49c866 151 // Master side hardware
JackB 0:b4f61c49c866 152 SPI _spi;
JackB 0:b4f61c49c866 153 DigitalOut _cs;
JackB 0:b4f61c49c866 154
JackB 0:b4f61c49c866 155 // Device configuration discovered through sfdp
JackB 0:b4f61c49c866 156 bd_size_t _size;
JackB 0:b4f61c49c866 157
JackB 0:b4f61c49c866 158 // Internal functions
JackB 0:b4f61c49c866 159 int _wren();
JackB 0:b4f61c49c866 160 int _sync();
JackB 0:b4f61c49c866 161 void _cmdread(uint8_t op, uint32_t addrc, uint32_t retc,
JackB 0:b4f61c49c866 162 uint32_t addr, uint8_t *rets);
JackB 0:b4f61c49c866 163 void _cmdwrite(uint8_t op, uint32_t addrc, uint32_t argc,
JackB 0:b4f61c49c866 164 uint32_t addr, const uint8_t *args);
JackB 0:b4f61c49c866 165 };
JackB 0:b4f61c49c866 166
JackB 0:b4f61c49c866 167
JackB 0:b4f61c49c866 168 #endif /* MBED_SPIF_BLOCK_DEVICE_H */