LibDriver AT24CXX
Loading...
Searching...
No Matches
driver_at24cxx.c
Go to the documentation of this file.
1
37
38#include "driver_at24cxx.h"
39
43#define CHIP_NAME "Microchip AT24CXX"
44#define MANUFACTURER_NAME "Microchip"
45#define SUPPLY_VOLTAGE_MIN 1.7f
46#define SUPPLY_VOLTAGE_MAX 5.5f
47#define MAX_CURRENT 5.0f
48#define TEMPERATURE_MIN -40.0f
49#define TEMPERATURE_MAX 85.0f
50#define DRIVER_VERSION 2000
51
63{
64 if (handle == NULL) /* check handle */
65 {
66 return 2; /* return error */
67 }
68 if (handle->debug_print == NULL) /* check debug_print */
69 {
70 return 3; /* return error */
71 }
72 if (handle->iic_init == NULL) /* check iic_init */
73 {
74 handle->debug_print("at24cxx: iic_init is null.\n"); /* iic_init is null */
75
76 return 3; /* return error */
77 }
78 if (handle->iic_deinit == NULL) /* check iic_deinit */
79 {
80 handle->debug_print("at24cxx: iic_deinit is null.\n"); /* iic_deinit is null */
81
82 return 3; /* return error */
83 }
84 if (handle->iic_read == NULL) /* check iic_read */
85 {
86 handle->debug_print("at24cxx: iic_read is null.\n"); /* iic_read is null */
87
88 return 3; /* return error */
89 }
90 if (handle->iic_write == NULL) /* check iic_write */
91 {
92 handle->debug_print("at24cxx: iic_write is null.\n"); /* iic_write is null */
93
94 return 3; /* return error */
95 }
96 if (handle->iic_read_address16 == NULL) /* check iic_read_address16 */
97 {
98 handle->debug_print("at24cxx: iic_read_address16 is null.\n"); /* iic_read_address16 is null */
99
100 return 3; /* return error */
101 }
102 if (handle->iic_write_address16 == NULL) /* check iic_write_address16 */
103 {
104 handle->debug_print("at24cxx: iic_write_address16 is null.\n"); /* iic_write_address16 is null */
105
106 return 3; /* return error */
107 }
108 if (handle->delay_ms == NULL) /* check delay_ms */
109 {
110 handle->debug_print("at24cxx: delay_ms is null.\n"); /* delay_ms is null */
111
112 return 3; /* return error */
113 }
114
115 if (handle->iic_init() != 0) /* iic init */
116 {
117 handle->debug_print("at24cxx: iic init failed.\n"); /* iic init failed */
118
119 return 1; /* return error */
120 }
121 handle->inited = 1; /* flag finish initialization */
122
123 return 0; /* success return 0 */
124}
125
137{
138 if (handle == NULL) /* check handle */
139 {
140 return 2; /* return error */
141 }
142 if (handle->inited != 1) /* check handle initialization */
143 {
144 return 3; /* return error */
145 }
146
147 if (handle->iic_deinit() != 0) /* iic deinit */
148 {
149 handle->debug_print("at24cxx: iic deinit failed.\n"); /* iic deinit failed */
150
151 return 1; /* return error */
152 }
153 handle->inited = 0; /* flag close */
154
155 return 0; /* success return 0 */
156}
157
168{
169 if (handle == NULL) /* check handle */
170 {
171 return 2; /* return error */
172 }
173
174 handle->id = (uint32_t)type; /* set id */
175
176 return 0; /* success return 0 */
177}
178
189{
190 if (handle == NULL) /* check handle */
191 {
192 return 2; /* return error */
193 }
194
195 *type = (at24cxx_t)(handle->id); /* get id */
196
197 return 0; /* success return 0 */
198}
199
210{
211 if (handle == NULL) /* check handle */
212 {
213 return 2; /* return error */
214 }
215
216 handle->iic_addr = 0xA0; /* set iic addr */
217 handle->iic_addr |= addr_pin << 1; /* set iic address */
218
219 return 0; /* success return 0 */
220}
221
232{
233 if (handle == NULL) /* check handle */
234 {
235 return 2; /* return error */
236 }
237
238 *addr_pin = (at24cxx_address_t)((handle->iic_addr & (~0xA0)) >> 1); /* get iic address */
239
240 return 0; /* success return 0 */
241}
242
257uint8_t at24cxx_read(at24cxx_handle_t *handle, uint32_t address, uint8_t *buf, uint16_t len)
258{
259 if (handle == NULL) /* check handle */
260 {
261 return 2; /* return error */
262 }
263 if (handle->inited != 1) /* check handle initialization */
264 {
265 return 3; /* return error */
266 }
267 if ((address + len) > handle->id) /* check length */
268 {
269 handle->debug_print("at24cxx: read out of range.\n"); /* read out of range */
270
271 return 4; /* return error */
272 }
273
274 if (handle->id > (uint32_t)AT24C16) /* choose id to set different address */
275 {
276 if (handle->iic_read_address16((uint8_t)(handle->iic_addr + ((address / 65536) << 1)),
277 address % 65536, buf,
278 len) != 0) /* read data */
279 {
280 handle->debug_print("at24cxx: read failed.\n"); /* read failed */
281
282 return 1; /* return error */
283 }
284 }
285 else
286 {
287 if (handle->iic_read((uint8_t)(handle->iic_addr + ((address / 256) << 1)), address % 256,
288 buf, len) != 0) /* read data */
289 {
290 handle->debug_print("at24cxx: read failed.\n"); /* read failed */
291
292 return 1; /* return error */
293 }
294 }
295
296 return 0; /* success return 0 */
297}
298
313uint8_t at24cxx_write(at24cxx_handle_t *handle, uint32_t address, uint8_t *buf, uint16_t len)
314{
315 uint16_t page_remain;
316 uint16_t page_div;
317 uint16_t page_delay_ms;
318
319 if (handle == NULL) /* check handle */
320 {
321 return 2; /* return error */
322 }
323 if (handle->inited != 1) /* check handle initialization */
324 {
325 return 3; /* return error */
326 }
327 if ((address + len) > handle->id) /* check length */
328 {
329 handle->debug_print("at24cxx: write out of range.\n"); /* write out of range */
330
331 return 4; /* return error */
332 }
333
334 switch ((uint32_t)handle->id) /* choose id */
335 {
336 case AT24C01 : /* 01 */
337 {
338 page_div = 8; /* 8 bytes */
339 page_delay_ms = 6; /* 6 ms */
340
341 break; /* break */
342 }
343 case AT24C02 : /* 02 */
344 {
345 page_div = 8; /* 8 bytes */
346 page_delay_ms = 6; /* 6 ms */
347
348 break; /* break */
349 }
350 case AT24C04 : /* 04 */
351 {
352 page_div = 16; /* 16 bytes */
353 page_delay_ms = 6; /* 6 ms */
354
355 break; /* break */
356 }
357 case AT24C08 : /* 08 */
358 {
359 page_div = 16; /* 16 bytes */
360 page_delay_ms = 6; /* 6 ms */
361
362 break; /* break */
363 }
364 case AT24C16 : /* 16 */
365 {
366 page_div = 16; /* 16 bytes */
367 page_delay_ms = 6; /* 6 ms */
368
369 break; /* break */
370 }
371 case AT24C32 : /* 32 */
372 {
373 page_div = 32; /* 32 bytes */
374 page_delay_ms = 6; /* 6 ms */
375
376 break; /* break */
377 }
378 case AT24C64 : /* 64 */
379 {
380 page_div = 32; /* 32 bytes */
381 page_delay_ms = 6; /* 6 ms */
382
383 break; /* break */
384 }
385 case AT24C128 : /* 128 */
386 {
387 page_div = 64; /* 64 bytes */
388 page_delay_ms = 6; /* 6 ms */
389
390 break; /* break */
391 }
392 case AT24C256 : /* 256 */
393 {
394 page_div = 64; /* 64 bytes */
395 page_delay_ms = 6; /* 6 ms */
396
397 break; /* break */
398 }
399 case AT24C512 : /* 512 */
400 {
401 page_div = 128; /* 128 bytes */
402 page_delay_ms = 6; /* 6 ms */
403
404 break; /* break */
405 }
406 case AT24CM01 : /* cm01 */
407 {
408 page_div = 256; /* 256 bytes */
409 page_delay_ms = 6; /* 6 ms */
410
411 break; /* break */
412 }
413 case AT24CM02 : /* cm02 */
414 {
415 page_div = 256; /* 256 bytes */
416 page_delay_ms = 11; /* 11 ms */
417
418 break; /* break */
419 }
420 default : /* default */
421 {
422 page_div = 8; /* 8 bytes */
423 page_delay_ms = 6; /* 6 ms */
424
425 break; /* break */
426 }
427 }
428
429 page_remain = (uint16_t)(page_div - address % page_div); /* set page remain */
430 if (len <= page_remain) /* check length */
431 {
432 page_remain = (uint16_t)len; /* set page remain */
433 }
434 if (handle->id > (uint32_t)AT24C16) /* check id */
435 {
436 while (1)
437 {
438 if (handle->iic_write_address16((uint8_t)(handle->iic_addr + ((address / 65536) << 1)),
439 address % 65536, buf,
440 page_remain) != 0) /* write page */
441 {
442 handle->debug_print("at24cxx: write failed.\n"); /* write failed */
443
444 return 1; /* return error */
445 }
446 handle->delay_ms(page_delay_ms); /* wait ok */
447 if (page_remain == len) /* check break */
448 {
449 break; /* break */
450 }
451 else
452 {
453 address += page_remain; /* address increase */
454 buf += page_remain; /* buffer point increase */
455 len -= page_remain; /* length decrease */
456 if (len < page_div) /* check length */
457 {
458 page_remain = (uint16_t)len; /* set the rest length */
459 }
460 else
461 {
462 page_remain = page_div; /* set page */
463 }
464 }
465 }
466 }
467 else
468 {
469 while (1)
470 {
471 if (handle->iic_write((uint8_t)(handle->iic_addr + ((address / 256) << 1)), address % 256, buf,
472 page_remain) != 0) /* write page */
473 {
474 handle->debug_print("at24cxx: write failed.\n"); /* write failed */
475
476 return 1; /* return error */
477 }
478 handle->delay_ms(page_delay_ms); /* wait ok */
479 if (page_remain == len) /* check break */
480 {
481 break; /* break */
482 }
483 else
484 {
485 address += page_remain; /* address increase */
486 buf += page_remain; /* buffer point increase */
487 len -= page_remain; /* length decrease */
488 if (len < page_div) /* check length */
489 {
490 page_remain = (uint16_t)len; /* set the rest length */
491 }
492 else
493 {
494 page_remain = page_div; /* set page */
495 }
496 }
497 }
498 }
499
500 return 0; /* success return 0 */
501}
502
512{
513 if (info == NULL) /* check handle */
514 {
515 return 2; /* return error */
516 }
517
518 memset(info, 0, sizeof(at24cxx_info_t)); /* initialize at24cxx info structure */
519 strncpy(info->chip_name, CHIP_NAME, 32); /* copy chip name */
520 strncpy(info->manufacturer_name, MANUFACTURER_NAME, 32); /* copy manufacturer name */
521 strncpy(info->interface, "IIC", 8); /* copy interface name */
522 info->supply_voltage_min_v = SUPPLY_VOLTAGE_MIN; /* set minimal supply voltage */
523 info->supply_voltage_max_v = SUPPLY_VOLTAGE_MAX; /* set maximum supply voltage */
524 info->max_current_ma = MAX_CURRENT; /* set maximum current */
525 info->temperature_max = TEMPERATURE_MAX; /* set maximum temperature */
526 info->temperature_min = TEMPERATURE_MIN; /* set minimal temperature */
527 info->driver_version = DRIVER_VERSION; /* set driver version */
528
529 return 0; /* success return 0 */
530}
#define MAX_CURRENT
#define SUPPLY_VOLTAGE_MAX
#define TEMPERATURE_MAX
#define MANUFACTURER_NAME
#define TEMPERATURE_MIN
#define SUPPLY_VOLTAGE_MIN
#define CHIP_NAME
chip information definition
#define DRIVER_VERSION
driver at24cxx header file
uint8_t at24cxx_set_type(at24cxx_handle_t *handle, at24cxx_t type)
set the chip type
uint8_t at24cxx_get_addr_pin(at24cxx_handle_t *handle, at24cxx_address_t *addr_pin)
get the chip address pin
uint8_t at24cxx_init(at24cxx_handle_t *handle)
initialize the chip
struct at24cxx_info_s at24cxx_info_t
at24cxx information structure definition
uint8_t at24cxx_read(at24cxx_handle_t *handle, uint32_t address, uint8_t *buf, uint16_t len)
read bytes from the chip
at24cxx_t
at24cxx type enumeration definition
uint8_t at24cxx_deinit(at24cxx_handle_t *handle)
close the chip
struct at24cxx_handle_s at24cxx_handle_t
at24cxx handle structure definition
uint8_t at24cxx_write(at24cxx_handle_t *handle, uint32_t address, uint8_t *buf, uint16_t len)
write bytes to the chip
at24cxx_address_t
at24cxx address enumeration definition
uint8_t at24cxx_info(at24cxx_info_t *info)
get chip's information
uint8_t at24cxx_set_addr_pin(at24cxx_handle_t *handle, at24cxx_address_t addr_pin)
set the chip address pin
uint8_t at24cxx_get_type(at24cxx_handle_t *handle, at24cxx_t *type)
get the chip type
@ AT24CM01
@ AT24C512
@ AT24C256
@ AT24C01
@ AT24CM02
@ AT24C32
@ AT24C08
@ AT24C128
@ AT24C64
@ AT24C16
@ AT24C02
@ AT24C04
void(* delay_ms)(uint32_t ms)
uint8_t(* iic_read_address16)(uint8_t addr, uint16_t reg, uint8_t *buf, uint16_t len)
void(* debug_print)(const char *const fmt,...)
uint8_t(* iic_init)(void)
uint8_t(* iic_write_address16)(uint8_t addr, uint16_t reg, uint8_t *buf, uint16_t len)
uint8_t(* iic_write)(uint8_t addr, uint8_t reg, uint8_t *buf, uint16_t len)
uint8_t(* iic_read)(uint8_t addr, uint8_t reg, uint8_t *buf, uint16_t len)
uint8_t(* iic_deinit)(void)
uint32_t driver_version
char manufacturer_name[32]