PokittoLib is the library needed for programming the Pokitto DIY game console (www.pokitto.com)
Dependents: YATTT sd_map_test cPong SnowDemo ... more
PokittoLib
Library for programming Pokitto hardware
How to Use
- Import this library to online compiler (see button "import" on the right hand side
- DO NOT import mbed-src anymore, a better version is now included inside PokittoLib
- Change My_settings.h according to your project
- Start coding!
POKITTO_CORE/PokittoCookie.cpp@51:113b1d84c34f, 2018-07-01 (annotated)
- Committer:
- Pokitto
- Date:
- Sun Jul 01 06:32:10 2018 +0000
- Revision:
- 51:113b1d84c34f
- Child:
- 58:5f58a2846a20
PokittoCookie and faster Mode2 and Mode13 added
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
Pokitto | 51:113b1d84c34f | 1 | /**************************************************************************/ |
Pokitto | 51:113b1d84c34f | 2 | /*! |
Pokitto | 51:113b1d84c34f | 3 | @file PokittoCookie.cpp |
Pokitto | 51:113b1d84c34f | 4 | @author Jonne Valola |
Pokitto | 51:113b1d84c34f | 5 | |
Pokitto | 51:113b1d84c34f | 6 | @section LICENSE |
Pokitto | 51:113b1d84c34f | 7 | |
Pokitto | 51:113b1d84c34f | 8 | Software License Agreement (BSD License) |
Pokitto | 51:113b1d84c34f | 9 | |
Pokitto | 51:113b1d84c34f | 10 | Copyright (c) 2018, Jonne Valola |
Pokitto | 51:113b1d84c34f | 11 | All rights reserved. |
Pokitto | 51:113b1d84c34f | 12 | |
Pokitto | 51:113b1d84c34f | 13 | Redistribution and use in source and binary forms, with or without |
Pokitto | 51:113b1d84c34f | 14 | modification, are permitted provided that the following conditions are met: |
Pokitto | 51:113b1d84c34f | 15 | 1. Redistributions of source code must retain the above copyright |
Pokitto | 51:113b1d84c34f | 16 | notice, this list of conditions and the following disclaimer. |
Pokitto | 51:113b1d84c34f | 17 | 2. Redistributions in binary form must reproduce the above copyright |
Pokitto | 51:113b1d84c34f | 18 | notice, this list of conditions and the following disclaimer in the |
Pokitto | 51:113b1d84c34f | 19 | documentation and/or other materials provided with the distribution. |
Pokitto | 51:113b1d84c34f | 20 | 3. Neither the name of the copyright holders nor the |
Pokitto | 51:113b1d84c34f | 21 | names of its contributors may be used to endorse or promote products |
Pokitto | 51:113b1d84c34f | 22 | derived from this software without specific prior written permission. |
Pokitto | 51:113b1d84c34f | 23 | |
Pokitto | 51:113b1d84c34f | 24 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS'' AND ANY |
Pokitto | 51:113b1d84c34f | 25 | EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
Pokitto | 51:113b1d84c34f | 26 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
Pokitto | 51:113b1d84c34f | 27 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY |
Pokitto | 51:113b1d84c34f | 28 | DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
Pokitto | 51:113b1d84c34f | 29 | (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
Pokitto | 51:113b1d84c34f | 30 | LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
Pokitto | 51:113b1d84c34f | 31 | ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
Pokitto | 51:113b1d84c34f | 32 | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
Pokitto | 51:113b1d84c34f | 33 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
Pokitto | 51:113b1d84c34f | 34 | */ |
Pokitto | 51:113b1d84c34f | 35 | /**************************************************************************/ |
Pokitto | 51:113b1d84c34f | 36 | |
Pokitto | 51:113b1d84c34f | 37 | #include "Pokitto_settings.h" |
Pokitto | 51:113b1d84c34f | 38 | #include "Pokitto.h" |
Pokitto | 51:113b1d84c34f | 39 | #include "PokittoCookie.h" |
Pokitto | 51:113b1d84c34f | 40 | |
Pokitto | 51:113b1d84c34f | 41 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 42 | #else |
Pokitto | 51:113b1d84c34f | 43 | #include "PokittoSimulator.h" |
Pokitto | 51:113b1d84c34f | 44 | #endif |
Pokitto | 51:113b1d84c34f | 45 | |
Pokitto | 51:113b1d84c34f | 46 | using namespace Pokitto; |
Pokitto | 51:113b1d84c34f | 47 | |
Pokitto | 51:113b1d84c34f | 48 | //char Cookie::_key[SBKEYSIZE]; |
Pokitto | 51:113b1d84c34f | 49 | //char Cookie::_keyorder; |
Pokitto | 51:113b1d84c34f | 50 | //bool Cookie::_status; |
Pokitto | 51:113b1d84c34f | 51 | |
Pokitto | 51:113b1d84c34f | 52 | #define HARDCODEDOFFSET 25 //bypasses Cookie parent instance general data (that does not need to be saved in EEPROM) |
Pokitto | 51:113b1d84c34f | 53 | |
Pokitto | 51:113b1d84c34f | 54 | Cookie::Cookie() { |
Pokitto | 51:113b1d84c34f | 55 | _status = false; |
Pokitto | 51:113b1d84c34f | 56 | _keyorder = SBINVALIDSLOT; |
Pokitto | 51:113b1d84c34f | 57 | } |
Pokitto | 51:113b1d84c34f | 58 | |
Pokitto | 51:113b1d84c34f | 59 | int Cookie::initialize() { |
Pokitto | 51:113b1d84c34f | 60 | //initialize is called from begin() and can be called several times during program run |
Pokitto | 51:113b1d84c34f | 61 | int datasize = _datasize; |
Pokitto | 51:113b1d84c34f | 62 | // check if key already exists |
Pokitto | 51:113b1d84c34f | 63 | _keyorder = exists(_key); |
Pokitto | 51:113b1d84c34f | 64 | if (_keyorder < SBMAXKEYS) { |
Pokitto | 51:113b1d84c34f | 65 | // key already exists |
Pokitto | 51:113b1d84c34f | 66 | // check amount of existing storage reserved for cookie |
Pokitto | 51:113b1d84c34f | 67 | datasize -= getAssignedBlocks()*SBBLOCKSIZE; |
Pokitto | 51:113b1d84c34f | 68 | if (datasize<=0) { |
Pokitto | 51:113b1d84c34f | 69 | // the size of data matches the size requested |
Pokitto | 51:113b1d84c34f | 70 | // therefore retrieve data from storage |
Pokitto | 51:113b1d84c34f | 71 | _status = true; //were good to go |
Pokitto | 51:113b1d84c34f | 72 | loadCookie(); |
Pokitto | 51:113b1d84c34f | 73 | } else { |
Pokitto | 51:113b1d84c34f | 74 | // if that does not cover the whole size (maybe a newer version of program, who knows) |
Pokitto | 51:113b1d84c34f | 75 | // then do not load but reserve more blocks and store a new version |
Pokitto | 51:113b1d84c34f | 76 | while (datasize>0) { |
Pokitto | 51:113b1d84c34f | 77 | if(reserveBlock()) datasize -= SBBLOCKSIZE; |
Pokitto | 51:113b1d84c34f | 78 | else return SBNOTENOUGHBLOCKSFREE; //no space to allocate |
Pokitto | 51:113b1d84c34f | 79 | } |
Pokitto | 51:113b1d84c34f | 80 | _status = true; //were good to go |
Pokitto | 51:113b1d84c34f | 81 | eraseKeytableEntry(_keyorder); |
Pokitto | 51:113b1d84c34f | 82 | writeKeyToKeytable(_key,_keyorder); // write the key in the key table in EEPROM |
Pokitto | 51:113b1d84c34f | 83 | saveCookie(); |
Pokitto | 51:113b1d84c34f | 84 | } |
Pokitto | 51:113b1d84c34f | 85 | } else { |
Pokitto | 51:113b1d84c34f | 86 | // new key needed |
Pokitto | 51:113b1d84c34f | 87 | // check if we have free keyslots |
Pokitto | 51:113b1d84c34f | 88 | _keyorder = getFreeKeytableSlot(); |
Pokitto | 51:113b1d84c34f | 89 | if (_keyorder>=SBMAXKEYS) return SBNOMOREKEYS; //no space for key |
Pokitto | 51:113b1d84c34f | 90 | // check if we have free storage blocks |
Pokitto | 51:113b1d84c34f | 91 | if (getFreeBlocks()*SBBLOCKSIZE<datasize) return SBNOTENOUGHBLOCKSFREE; //no space to allocate |
Pokitto | 51:113b1d84c34f | 92 | while (datasize>0) { |
Pokitto | 51:113b1d84c34f | 93 | //reserve enough blocks for the data until all data can fit |
Pokitto | 51:113b1d84c34f | 94 | if(reserveBlock()) datasize -= SBBLOCKSIZE; |
Pokitto | 51:113b1d84c34f | 95 | else return SBNOTENOUGHBLOCKSFREE; //no space to allocate |
Pokitto | 51:113b1d84c34f | 96 | } |
Pokitto | 51:113b1d84c34f | 97 | } |
Pokitto | 51:113b1d84c34f | 98 | _status = true; //were good to go |
Pokitto | 51:113b1d84c34f | 99 | eraseKeytableEntry(_keyorder); |
Pokitto | 51:113b1d84c34f | 100 | writeKeyToKeytable(_key,_keyorder); // write the key in the key table in EEPROM |
Pokitto | 51:113b1d84c34f | 101 | return 0; |
Pokitto | 51:113b1d84c34f | 102 | } |
Pokitto | 51:113b1d84c34f | 103 | |
Pokitto | 51:113b1d84c34f | 104 | int Cookie::begin(const char* idkey, int datasize, char* ptr) { |
Pokitto | 51:113b1d84c34f | 105 | _status=false; |
Pokitto | 51:113b1d84c34f | 106 | _datasize=datasize-HARDCODEDOFFSET;// warning! hardcoded! sizeof(this); //do not include the data of the parent Cookie instance |
Pokitto | 51:113b1d84c34f | 107 | _pointer = ptr + HARDCODEDOFFSET;// warning! hardcoded! sizeof(this); //point to the beginning of the inherited instance |
Pokitto | 51:113b1d84c34f | 108 | char _idkey[8]; |
Pokitto | 51:113b1d84c34f | 109 | // make _idkey exactly 8 readable characters long |
Pokitto | 51:113b1d84c34f | 110 | for (int t = 0 ; t < 8 ; t++) _idkey[t]=' '; |
Pokitto | 51:113b1d84c34f | 111 | for (int t = 0 ; t < 8 ; t++) {if (idkey[t]==0) break; _idkey[t]=idkey[t];} |
Pokitto | 51:113b1d84c34f | 112 | // clean Keytable of keys with no storage |
Pokitto | 51:113b1d84c34f | 113 | cleanKeytable(); |
Pokitto | 51:113b1d84c34f | 114 | memcpy(_key, _idkey, SBKEYSIZE); //store name of key |
Pokitto | 51:113b1d84c34f | 115 | initialize(); |
Pokitto | 51:113b1d84c34f | 116 | return 0; //success |
Pokitto | 51:113b1d84c34f | 117 | } |
Pokitto | 51:113b1d84c34f | 118 | |
Pokitto | 51:113b1d84c34f | 119 | bool Cookie::saveCookie() { |
Pokitto | 51:113b1d84c34f | 120 | if (!_status || !_pointer) initialize(); //reinitialize if needed |
Pokitto | 51:113b1d84c34f | 121 | if (!_status || !_pointer) return false; //return if initialize still failed |
Pokitto | 51:113b1d84c34f | 122 | char* p = _pointer; |
Pokitto | 51:113b1d84c34f | 123 | _head=0; |
Pokitto | 51:113b1d84c34f | 124 | _block=0; |
Pokitto | 51:113b1d84c34f | 125 | _block=findMyNextBlock(); |
Pokitto | 51:113b1d84c34f | 126 | for (int i=0; i<_datasize; i++) writeQueue(*p++); |
Pokitto | 51:113b1d84c34f | 127 | } |
Pokitto | 51:113b1d84c34f | 128 | |
Pokitto | 51:113b1d84c34f | 129 | bool Cookie::loadCookie() { |
Pokitto | 51:113b1d84c34f | 130 | if (!_status || !_pointer) return false; |
Pokitto | 51:113b1d84c34f | 131 | char* p = _pointer; |
Pokitto | 51:113b1d84c34f | 132 | _head=0; |
Pokitto | 51:113b1d84c34f | 133 | _block=0; |
Pokitto | 51:113b1d84c34f | 134 | _block=findMyNextBlock(); |
Pokitto | 51:113b1d84c34f | 135 | for (int i=0; i<_datasize; i++) *p++ = readQueue(); |
Pokitto | 51:113b1d84c34f | 136 | } |
Pokitto | 51:113b1d84c34f | 137 | |
Pokitto | 51:113b1d84c34f | 138 | void Cookie::deleteCookie() { |
Pokitto | 51:113b1d84c34f | 139 | if (!_status) return; |
Pokitto | 51:113b1d84c34f | 140 | // free all blocks held by Cookie |
Pokitto | 51:113b1d84c34f | 141 | for (int i=0; i<SBMAXBLOCKS; i++) { |
Pokitto | 51:113b1d84c34f | 142 | if (isMyBlock(i)) freeBlock(i); |
Pokitto | 51:113b1d84c34f | 143 | } |
Pokitto | 51:113b1d84c34f | 144 | // erase Cookie entry from keytable |
Pokitto | 51:113b1d84c34f | 145 | eraseKeytableEntry(_keyorder); |
Pokitto | 51:113b1d84c34f | 146 | // set status to deleted |
Pokitto | 51:113b1d84c34f | 147 | _status = false; |
Pokitto | 51:113b1d84c34f | 148 | } |
Pokitto | 51:113b1d84c34f | 149 | |
Pokitto | 51:113b1d84c34f | 150 | int Cookie::exists(const char* idkey) { |
Pokitto | 51:113b1d84c34f | 151 | for (int i=0; i< SBMAXKEYS; i++) { |
Pokitto | 51:113b1d84c34f | 152 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 153 | if(eeprom_read_byte((uint16_t*)(i*SBKEYSIZE))==idkey[0]) { |
Pokitto | 51:113b1d84c34f | 154 | int total=0; |
Pokitto | 51:113b1d84c34f | 155 | for (int j=0; j<SBKEYSIZE;j++) { |
Pokitto | 51:113b1d84c34f | 156 | if(eeprom_read_byte((uint16_t*)(i*SBKEYSIZE+j))==idkey[j]) total++; |
Pokitto | 51:113b1d84c34f | 157 | } |
Pokitto | 51:113b1d84c34f | 158 | if (total==SBKEYSIZE) return i; // return the keyslot number where key exists |
Pokitto | 51:113b1d84c34f | 159 | } |
Pokitto | 51:113b1d84c34f | 160 | #endif |
Pokitto | 51:113b1d84c34f | 161 | } |
Pokitto | 51:113b1d84c34f | 162 | return SBINVALIDSLOT; //not found |
Pokitto | 51:113b1d84c34f | 163 | } |
Pokitto | 51:113b1d84c34f | 164 | |
Pokitto | 51:113b1d84c34f | 165 | int Cookie::getFreeKeytableSlot() { |
Pokitto | 51:113b1d84c34f | 166 | int freeslot=SBINVALIDSLOT; |
Pokitto | 51:113b1d84c34f | 167 | for (int i=0; i<SBMAXKEYS; i++) { |
Pokitto | 51:113b1d84c34f | 168 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 169 | if (eeprom_read_byte((uint16_t*)(i*SBKEYSIZE))==0) {freeslot=i; break;} |
Pokitto | 51:113b1d84c34f | 170 | #endif |
Pokitto | 51:113b1d84c34f | 171 | } |
Pokitto | 51:113b1d84c34f | 172 | return freeslot; |
Pokitto | 51:113b1d84c34f | 173 | } |
Pokitto | 51:113b1d84c34f | 174 | |
Pokitto | 51:113b1d84c34f | 175 | int Cookie::getAssignedBlocks() { |
Pokitto | 51:113b1d84c34f | 176 | int assignedblocks=0; |
Pokitto | 51:113b1d84c34f | 177 | for (int i=0;i<SBMAXBLOCKS;i++) { |
Pokitto | 51:113b1d84c34f | 178 | if (isMyBlock(i)) assignedblocks++; |
Pokitto | 51:113b1d84c34f | 179 | } |
Pokitto | 51:113b1d84c34f | 180 | return assignedblocks; |
Pokitto | 51:113b1d84c34f | 181 | } |
Pokitto | 51:113b1d84c34f | 182 | |
Pokitto | 51:113b1d84c34f | 183 | int Cookie::getFreeBlocks() { |
Pokitto | 51:113b1d84c34f | 184 | int freeblocks=0; |
Pokitto | 51:113b1d84c34f | 185 | for (int i=0;i<SBMAXBLOCKS;i++) { |
Pokitto | 51:113b1d84c34f | 186 | if (isFreeBlock(i)) freeblocks++; |
Pokitto | 51:113b1d84c34f | 187 | } |
Pokitto | 51:113b1d84c34f | 188 | return freeblocks; |
Pokitto | 51:113b1d84c34f | 189 | } |
Pokitto | 51:113b1d84c34f | 190 | |
Pokitto | 51:113b1d84c34f | 191 | bool Cookie::isFreeBlock(int n) { |
Pokitto | 51:113b1d84c34f | 192 | if (n>=SBMAXBLOCKS) return false; |
Pokitto | 51:113b1d84c34f | 193 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 194 | if (!(eeprom_read_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+n))&0x80)) return true; //highest bit 0, its free |
Pokitto | 51:113b1d84c34f | 195 | #endif |
Pokitto | 51:113b1d84c34f | 196 | return false; //its not free |
Pokitto | 51:113b1d84c34f | 197 | } |
Pokitto | 51:113b1d84c34f | 198 | |
Pokitto | 51:113b1d84c34f | 199 | bool Cookie::isMyBlock(int n) { |
Pokitto | 51:113b1d84c34f | 200 | if (n>=SBMAXBLOCKS) return false; |
Pokitto | 51:113b1d84c34f | 201 | if (isFreeBlock(n)) return false; //"free" blocks can not be "reserved" at the same time! |
Pokitto | 51:113b1d84c34f | 202 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 203 | char temp; int address; |
Pokitto | 51:113b1d84c34f | 204 | address = (SBMAXKEYS*SBKEYSIZE+n); |
Pokitto | 51:113b1d84c34f | 205 | temp = eeprom_read_byte((uint16_t*)address); |
Pokitto | 51:113b1d84c34f | 206 | if ((temp&0x7F) ==_keyorder) return true; |
Pokitto | 51:113b1d84c34f | 207 | #endif |
Pokitto | 51:113b1d84c34f | 208 | return false; //its not your block |
Pokitto | 51:113b1d84c34f | 209 | } |
Pokitto | 51:113b1d84c34f | 210 | |
Pokitto | 51:113b1d84c34f | 211 | bool Cookie::blockIsOwnedBy(int n, int k) { |
Pokitto | 51:113b1d84c34f | 212 | if (n>=SBMAXBLOCKS) return false; |
Pokitto | 51:113b1d84c34f | 213 | if (k>=SBMAXKEYS) return false; |
Pokitto | 51:113b1d84c34f | 214 | if (isFreeBlock(n)) return false; //"free" blocks can not be "owned" by anyone |
Pokitto | 51:113b1d84c34f | 215 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 216 | char temp; int address; |
Pokitto | 51:113b1d84c34f | 217 | address = (SBMAXKEYS*SBKEYSIZE+n); |
Pokitto | 51:113b1d84c34f | 218 | temp = eeprom_read_byte((uint16_t*)address); |
Pokitto | 51:113b1d84c34f | 219 | if ((temp&0x7F) == k) return true; |
Pokitto | 51:113b1d84c34f | 220 | #endif |
Pokitto | 51:113b1d84c34f | 221 | return false; //its not your block |
Pokitto | 51:113b1d84c34f | 222 | } |
Pokitto | 51:113b1d84c34f | 223 | |
Pokitto | 51:113b1d84c34f | 224 | void Cookie::writeKeyToKeytable(const char* key, int slot) { |
Pokitto | 51:113b1d84c34f | 225 | for (int i=0; i<SBKEYSIZE; i++) { |
Pokitto | 51:113b1d84c34f | 226 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 227 | if (key[i]) eeprom_write_byte((uint16_t*)(slot*SBKEYSIZE+i),key[i]); |
Pokitto | 51:113b1d84c34f | 228 | else eeprom_write_byte((uint16_t*)(slot*SBKEYSIZE+i),0); |
Pokitto | 51:113b1d84c34f | 229 | #endif |
Pokitto | 51:113b1d84c34f | 230 | } |
Pokitto | 51:113b1d84c34f | 231 | } |
Pokitto | 51:113b1d84c34f | 232 | |
Pokitto | 51:113b1d84c34f | 233 | void Cookie::readKeytableEntry(int n, char* answer) { |
Pokitto | 51:113b1d84c34f | 234 | answer[8]=0; |
Pokitto | 51:113b1d84c34f | 235 | if (n >= SBMAXKEYS) n=SBMAXKEYS-1; |
Pokitto | 51:113b1d84c34f | 236 | for (int i=0; i<SBKEYSIZE; i++) { |
Pokitto | 51:113b1d84c34f | 237 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 238 | answer[i] = eeprom_read_byte((uint16_t*)(n*SBKEYSIZE+i)); |
Pokitto | 51:113b1d84c34f | 239 | #endif |
Pokitto | 51:113b1d84c34f | 240 | } |
Pokitto | 51:113b1d84c34f | 241 | } |
Pokitto | 51:113b1d84c34f | 242 | |
Pokitto | 51:113b1d84c34f | 243 | char Cookie::getBlockTableEntry(int n) { |
Pokitto | 51:113b1d84c34f | 244 | if (n>=SBMAXBLOCKS) return 0x80; // out of bounds will return a reserved block marker |
Pokitto | 51:113b1d84c34f | 245 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 246 | return eeprom_read_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+n)); |
Pokitto | 51:113b1d84c34f | 247 | #endif |
Pokitto | 51:113b1d84c34f | 248 | return 0x80; |
Pokitto | 51:113b1d84c34f | 249 | } |
Pokitto | 51:113b1d84c34f | 250 | |
Pokitto | 51:113b1d84c34f | 251 | void Cookie::readBlock(int n, char* data) { |
Pokitto | 51:113b1d84c34f | 252 | for (int i=0; i<SBBLOCKSIZE; i++) { |
Pokitto | 51:113b1d84c34f | 253 | data[i]=0; |
Pokitto | 51:113b1d84c34f | 254 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 255 | if (n < SBMAXBLOCKS) data[i] = eeprom_read_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+SBMAXBLOCKS+n*SBBLOCKSIZE+i)); |
Pokitto | 51:113b1d84c34f | 256 | #endif |
Pokitto | 51:113b1d84c34f | 257 | } |
Pokitto | 51:113b1d84c34f | 258 | } |
Pokitto | 51:113b1d84c34f | 259 | |
Pokitto | 51:113b1d84c34f | 260 | void Cookie::formatKeytable() { |
Pokitto | 51:113b1d84c34f | 261 | for (int j=0; j<SBMAXKEYS; j++) { |
Pokitto | 51:113b1d84c34f | 262 | for (int i=0; i<SBKEYSIZE; i++) { |
Pokitto | 51:113b1d84c34f | 263 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 264 | eeprom_write_byte((uint16_t*)(j*SBKEYSIZE+i),0); |
Pokitto | 51:113b1d84c34f | 265 | #endif |
Pokitto | 51:113b1d84c34f | 266 | } |
Pokitto | 51:113b1d84c34f | 267 | } |
Pokitto | 51:113b1d84c34f | 268 | } |
Pokitto | 51:113b1d84c34f | 269 | |
Pokitto | 51:113b1d84c34f | 270 | void Cookie::freeBlock(int n) { |
Pokitto | 51:113b1d84c34f | 271 | if (n >= SBMAXBLOCKS) return; //out of bounds |
Pokitto | 51:113b1d84c34f | 272 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 273 | // delete entry from blocktable |
Pokitto | 51:113b1d84c34f | 274 | eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+n),0); |
Pokitto | 51:113b1d84c34f | 275 | #endif |
Pokitto | 51:113b1d84c34f | 276 | for (int i=0; i<SBBLOCKSIZE;i++) { |
Pokitto | 51:113b1d84c34f | 277 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 278 | // wipe data in the block |
Pokitto | 51:113b1d84c34f | 279 | eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+SBMAXBLOCKS+n*SBBLOCKSIZE+i),0); |
Pokitto | 51:113b1d84c34f | 280 | #endif |
Pokitto | 51:113b1d84c34f | 281 | } |
Pokitto | 51:113b1d84c34f | 282 | } |
Pokitto | 51:113b1d84c34f | 283 | |
Pokitto | 51:113b1d84c34f | 284 | bool Cookie::reserveBlock() { |
Pokitto | 51:113b1d84c34f | 285 | for (int i=0; i<SBMAXBLOCKS;i++) { |
Pokitto | 51:113b1d84c34f | 286 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 287 | // reserve block from blocktable |
Pokitto | 51:113b1d84c34f | 288 | if (isFreeBlock(i)) { |
Pokitto | 51:113b1d84c34f | 289 | //free block found, mark it for us in the blocktable |
Pokitto | 51:113b1d84c34f | 290 | eeprom_write_byte((uint16_t*)(SBKEYSIZE*SBMAXKEYS+i),_keyorder | 0x80); |
Pokitto | 51:113b1d84c34f | 291 | return true; |
Pokitto | 51:113b1d84c34f | 292 | } |
Pokitto | 51:113b1d84c34f | 293 | #endif |
Pokitto | 51:113b1d84c34f | 294 | } |
Pokitto | 51:113b1d84c34f | 295 | return false; // no free block found |
Pokitto | 51:113b1d84c34f | 296 | } |
Pokitto | 51:113b1d84c34f | 297 | |
Pokitto | 51:113b1d84c34f | 298 | void Cookie::eraseKeytableEntry(int n) { |
Pokitto | 51:113b1d84c34f | 299 | if (n >= SBMAXKEYS) n=SBMAXKEYS-1; |
Pokitto | 51:113b1d84c34f | 300 | for (int i=0; i<SBKEYSIZE; i++) { |
Pokitto | 51:113b1d84c34f | 301 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 302 | eeprom_write_byte((uint16_t*)(n*SBKEYSIZE+i),0); |
Pokitto | 51:113b1d84c34f | 303 | #endif |
Pokitto | 51:113b1d84c34f | 304 | } |
Pokitto | 51:113b1d84c34f | 305 | } |
Pokitto | 51:113b1d84c34f | 306 | |
Pokitto | 51:113b1d84c34f | 307 | void Cookie::cleanKeytable() { |
Pokitto | 51:113b1d84c34f | 308 | //Remove any keys without blocks |
Pokitto | 51:113b1d84c34f | 309 | for (int entry=0; entry<SBMAXKEYS; entry++) { |
Pokitto | 51:113b1d84c34f | 310 | if (eeprom_read_byte((uint16_t*)(entry*SBKEYSIZE))) { |
Pokitto | 51:113b1d84c34f | 311 | bool isEmpty=true; |
Pokitto | 51:113b1d84c34f | 312 | for (int block=0; block<SBMAXBLOCKS; block++) if (blockIsOwnedBy(block,entry)) {isEmpty=false;break;} |
Pokitto | 51:113b1d84c34f | 313 | //this entry has no blocks reserved, so lets clean it from the keytable |
Pokitto | 51:113b1d84c34f | 314 | if (isEmpty) eraseKeytableEntry(entry); |
Pokitto | 51:113b1d84c34f | 315 | } |
Pokitto | 51:113b1d84c34f | 316 | } |
Pokitto | 51:113b1d84c34f | 317 | for (int block=0;block<SBMAXBLOCKS;block++) { |
Pokitto | 51:113b1d84c34f | 318 | int blockentry = eeprom_read_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+block)); |
Pokitto | 51:113b1d84c34f | 319 | if (blockentry&0x80) { |
Pokitto | 51:113b1d84c34f | 320 | blockentry &= 0x7F; |
Pokitto | 51:113b1d84c34f | 321 | bool isEmpty=true; |
Pokitto | 51:113b1d84c34f | 322 | for (int key=0;key<SBMAXKEYS;key++) { |
Pokitto | 51:113b1d84c34f | 323 | if (eeprom_read_byte((uint16_t*)(key*SBKEYSIZE))) {isEmpty=false;break;} |
Pokitto | 51:113b1d84c34f | 324 | } |
Pokitto | 51:113b1d84c34f | 325 | if (isEmpty) eeprom_write_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+block),0); |
Pokitto | 51:113b1d84c34f | 326 | } |
Pokitto | 51:113b1d84c34f | 327 | } |
Pokitto | 51:113b1d84c34f | 328 | } |
Pokitto | 51:113b1d84c34f | 329 | |
Pokitto | 51:113b1d84c34f | 330 | char Cookie::readQueue() { |
Pokitto | 51:113b1d84c34f | 331 | char data=0; |
Pokitto | 51:113b1d84c34f | 332 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 333 | int address; |
Pokitto | 51:113b1d84c34f | 334 | address = SBMAXKEYS*SBKEYSIZE+SBMAXBLOCKS+SBBLOCKSIZE*_block+_head%SBBLOCKSIZE; |
Pokitto | 51:113b1d84c34f | 335 | data=eeprom_read_byte((uint16_t*)address); |
Pokitto | 51:113b1d84c34f | 336 | #endif |
Pokitto | 51:113b1d84c34f | 337 | _head++; |
Pokitto | 51:113b1d84c34f | 338 | if (_head%SBBLOCKSIZE==0 && _head) { |
Pokitto | 51:113b1d84c34f | 339 | _block++; |
Pokitto | 51:113b1d84c34f | 340 | _block=findMyNextBlock(); |
Pokitto | 51:113b1d84c34f | 341 | } |
Pokitto | 51:113b1d84c34f | 342 | return data; |
Pokitto | 51:113b1d84c34f | 343 | } |
Pokitto | 51:113b1d84c34f | 344 | |
Pokitto | 51:113b1d84c34f | 345 | void Cookie::writeQueue(char data) { |
Pokitto | 51:113b1d84c34f | 346 | #ifndef POK_SIM |
Pokitto | 51:113b1d84c34f | 347 | eeprom_write_byte((uint16_t*)(SBMAXKEYS*SBKEYSIZE+SBMAXBLOCKS+SBBLOCKSIZE*_block+_head%SBBLOCKSIZE),data); |
Pokitto | 51:113b1d84c34f | 348 | #endif |
Pokitto | 51:113b1d84c34f | 349 | _head++; |
Pokitto | 51:113b1d84c34f | 350 | if (_head%SBBLOCKSIZE==0 && _head) { |
Pokitto | 51:113b1d84c34f | 351 | _block++; |
Pokitto | 51:113b1d84c34f | 352 | _block=findMyNextBlock(); |
Pokitto | 51:113b1d84c34f | 353 | } |
Pokitto | 51:113b1d84c34f | 354 | } |
Pokitto | 51:113b1d84c34f | 355 | |
Pokitto | 51:113b1d84c34f | 356 | int Cookie::findMyNextBlock() { |
Pokitto | 51:113b1d84c34f | 357 | if (!_status) return SBINVALIDBLOCK; |
Pokitto | 51:113b1d84c34f | 358 | for (int i=_block; i<SBMAXBLOCKS;i++) if (isMyBlock(i)) return i; |
Pokitto | 51:113b1d84c34f | 359 | } |
Pokitto | 51:113b1d84c34f | 360 | |
Pokitto | 51:113b1d84c34f | 361 | |
Pokitto | 51:113b1d84c34f | 362 |