Repurpose a Single Use Libero CB temperature logger - Page 1
Forum section: electronics / general

author: monthlybasil
author_rank: Newbie
timestamp: September 30, 2022, 12:51:42 am
content: I have a single use temperature logger, that is apparently useless when it has been received at the delivery location and read by plugging it in.Not happy at this piece having no further use, I wanted to see if there is another purpose for this. So I opened it up and removed the battery to try and reset it. No dice. It still displayed Stop.I tried holding the start stop button while inserting the battery and bLdr is displayed. Plugging it in now, instead of showing the compiled PDF, shows an empty folder.I'm assuming that, provided a new firmware file at this stage, the temperature logger could be customised and then used to check if the fridge has stopped running while on holidays, log min and max temps, and maybe something awesome that I haven't thought of yet.I'm out of my depth and need the next step.Any ideas or assistance is appreciated.

author: eutectique
author_rank: Frequent Contributor
timestamp: September 30, 2022, 04:50:08 am
content: QuoteCan you create an empty pdf file there?

author: monthlybasil
author_rank: Newbie
timestamp: September 30, 2022, 05:27:48 am
content: I didn't want to try anything just yet, I'm assuming bLdr is shorthand for bootloader, so either that's when it can be programmed, either with a .bin or a suitable piece of software.But I suppose if I can get it to bootloader I can do pretty much anything, because I can get it back to this point and try again?I was going to try a 'blink' firmware, that flashes each segment on the LCD one by one.Is this arduino ide level? Or do I need to make it in platformIO or something else? I've not messed with these ICs before.

author: Ian.M
author_rank: Super Contributor
timestamp: September 30, 2022, 05:34:17 am
content: I agree 'bLdr' probably stands for boot-loader, i.e. its expecting new firmware. It may be looking for a firmware file to be written to the mass storage device it presents as, possibly encrypted and/or in a proprietary format, or it may expect it over some other interface, connected via pogo pins to the test pads on the underside of the PCB.If you study the datasheet of the STM32L073CZT6 MCU, and do a bit of research you can probably figure out how to wipe the chip and get it into a more standard bootloader mode so you can use your own firmware. If you haven't done STM32 development previously you've got a long steep road ahead of you! It certainly isn't going to be as easy as adding a new board to the Arduino IDE, as there don't seem to be any using that specific MCU.

author: voltsandjolts
author_rank: Unknown
timestamp: September 30, 2022, 09:46:41 am
content: There's a chance that the oem firmware displays 'bLdr' and then jumps to the built-in STM32 usb dfu bootloader.Might be worth tryingstm32 dFuSe.

author: eutectique
author_rank: Frequent Contributor
timestamp: September 30, 2022, 10:37:46 am
content: Quote from: monthlybasil on September 30, 2022, 05:27:48 amIf you followed Microcontrollers section for a couple of past days, you've probably noticed three discussions dedicated to tools:https://www.eevblog.com/forum/microcontrollers/lets-discuss-telluriums-tutorial/https://www.eevblog.com/forum/microcontrollers/rant-why-i-dumped-platform-io-ide-after-a-week/https://www.eevblog.com/forum/microcontrollers/is-st-cube-ide-a-piece-of-buggy-crap/

author: ozcar
author_rank: Frequent Contributor
timestamp: September 30, 2022, 08:03:11 pm
content: Quote from: Ian.M on September 30, 2022, 05:34:17 amThe "official STM32DUINO" core does include an entry for "Generic L073CZYx" - should be "close enough".

author: monthlybasil
author_rank: Newbie
timestamp: October 02, 2022, 05:15:39 am
content: Here's what I have so far.I'm not 100% sure on the battery level or the temperature probe sensing circuits, but the LCD segments I'm confident with.LCD Segmentsx x x COM3 COM2 COM1 COM0 x x xSEG0 SEG1 SEG5 SEG6 SEG10 SEG11 SEG12 SEG13 SEG14 SEG15PA3 temp_sense_enable? Set high to power the NTC?PA5 temp_sense? Temp read ADC on this pinPH0 button?PH1 batt level? Sense battery level?PC14 RCC Ceramic ClockPC15 RCC Ceramic Clock

author: voltsandjolts
author_rank: Unknown
timestamp: October 02, 2022, 08:55:58 am
content: Manufacturer datasheet for this temperature logger ishere.Product line web page ishere.Do you have an example of the PDF produced by this logger?I'm just interested to see how the PDF is created by this mcu.

author: monthlybasil
author_rank: Newbie
timestamp: October 02, 2022, 11:45:25 am
content: So I am able to short the boot pin and I think I can upload new firmware to it.next challenge is how to cycle through the multiplexed lcd elements to identify the lcd pinouts.I have thought about driving them as GPIO pins, but I need to apply ac to them. So probably the best bet is to write something in STM32CubeIDE but I dont know how to initialise the LCD.this video was helpful with the methodology to determine the pinoutseating this elephant one bite at a time.

author: voltsandjolts
author_rank: Unknown
timestamp: October 02, 2022, 12:47:35 pm
content: Thanks for the info.Quote from: monthlybasil on October 02, 2022, 11:45:25 amWhat PC software are you using, STM32 DfuSe?

author: monthlybasil
author_rank: Newbie
timestamp: October 05, 2022, 11:14:16 am
content: So I've been researching (https://st-onlinetraining.s3.amazonaws.com/STM32L4_Peripheral_Liquid_Crystal_Display_interface_(LCD)/index.html) and messing around, and I cant get anything to display on the LCD. would the code below produce anything, assuming the other voltages and clk settings are suitable?Code:/* USER CODE BEGIN WHILE */while (1){HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER0, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER1, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER2, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER3, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER4, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER5, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);HAL_LCD_Clear(&hlcd);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER7, 0x0000, 32);HAL_LCD_UpdateDisplayRequest(&hlcd); HAL_Delay(500);/* USER CODE END WHILE */

author: monthlybasil
author_rank: Newbie
timestamp: October 07, 2022, 07:54:16 am
content: So LCD is workingNeeded to set the LCD Contrast Control to 2.68V.The following illuminates all the segmentsCode:while (1){uint16_t screendata1 = 0b1111110001100011;uint16_t screendata2 = 0b1111110001100011;uint16_t screendata3 = 0b1111110001100011;uint16_t screendata4 = 0b1111110001000011;HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER0, 0xFC63, screendata1);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER2, 0xFC63, screendata2);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER4, 0xFC63, screendata3);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 0xFC43, screendata4);HAL_LCD_UpdateDisplayRequest(&hlcd);HAL_Delay(1000);HAL_LCD_Clear(&hlcd);HAL_Delay(1000);/* USER CODE END WHILE */And the segments are mapped out as:Code:RAM REG15141312111098765432100LowBatt4b4a3b3a2b2a1b1aRUN2Profile4g4f3g3f2g2f1g1fCROSS4degC4c4e3c3e2c2e1c1eTICK6degF%4ddp33ddp22d1dDIAGnow to mess with ADC to get a temp readout over serial.

author: monthlybasil
author_rank: Newbie
timestamp: October 10, 2022, 11:42:00 am
content: Can anyone help me with changing the LCD Segment Pins so they are in order, or manipulate the order of them so I dont have two 3 bit gaps in the pin table? I have not had much luck with googling a solution.

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 12, 2022, 02:18:17 am
content: I'd use a combination of indexing tables and functions, using different functions for symbols (lowbatt, etc), which only need to modify one bit of a single register, and the alphanuneric segments, where all memory registers need to be modified to construct the final character.That way you step to high level functions, making the access much easier.This is enough as an initial test, untested, written using the phoneCode:#include <stdbool.h>#include <stdint.h>#define icon_count 9#define ON true#define OFF falsetypedef enum {icon_lowbatt = 0,icon_run,icon_profile,icon_cross,icon_degC,icon_tick,icon_degF,icon_percent,icon_diag,} icon_name_t;typedef struct{const uint8_t reg;const uint8_t mask;} icon_data_t;icon_data_t icon_data = { = { LCD_RAM_REGISTER0, 15 }, = { LCD_RAM_REGISTER0, 0 }, = { LCD_RAM_REGISTER2, 15 }, = { LCD_RAM_REGISTER2, 0 }, = { LCD_RAM_REGISTER4, 15 }, = { LCD_RAM_REGISTER4, 0 }, = { LCD_RAM_REGISTER6, 15 }, = { LCD_RAM_REGISTER6, 14 }, = { LCD_RAM_REGISTER6, 0 },};void set_icon(icon_name_t i, bool enable){uint16_t mask = 1 << icon_data.mask;HAL_LCD_Write(&hlcd, icon_data.reg, mask, ( enable ? mask : 0 ) );HAL_LCD_UpdateDisplayRequest(&hlcd);}void main(void){while(1){set_icon(icon_run, ON);HAL_Delay(1000);set_icon(icon_run, OFF);HAL_Delay(1000);}}

author: DavidAlfa
author_rank: Super Contributor
timestamp: October 12, 2022, 03:59:36 am
content: Digits test. Probably could be simplified, but it lets you see the mechanics very easily.Code:#include <stdbool.h>#include <stdint.h>#define char_count 4#define seg_count 8#define A 1#define B 2#define C 4#define D 8#define E 16#define F 32#define G 64const uint8_t digits[] = {(A+B+C+D+E+F), //0(B+C), //1(A+B+G+E+D), //2(A+B+C+D+G), //3(F+G+B+C), //4(A+F+G+C+D), //5(A+F+E+D+C+G), //6(A+B+C), //7(A+B+C+D+E+F+G), //8(D+C+B+A+F+G), //9};typedef enum {seg_a = 0,seg_b,seg_c,seg_d,seg_e,seg_f,seg_g,seg_dp,} seg_name_t;typedef enum {char_1 = 0,char_2,char_3,char_4,} char_name_t;typedef struct{const uint8_t reg;const uint8_t mask;} seg_data_t;seg_data_t seg_data = { = { = { LCD_RAM_REGISTER0, 1 }, = { LCD_RAM_REGISTER0, 5 }, = { LCD_RAM_REGISTER4, 5 }, = { LCD_RAM_REGISTER6, 1 }, = { LCD_RAM_REGISTER4, 1 }, = { LCD_RAM_REGISTER2, 1 }, = { LCD_RAM_REGISTER2, 5 },}, = { = { LCD_RAM_REGISTER0, 6 }, = { LCD_RAM_REGISTER0, 10 }, = { LCD_RAM_REGISTER4, 10 }, = { LCD_RAM_REGISTER6, 6 }, = { LCD_RAM_REGISTER4, 6 }, = { LCD_RAM_REGISTER2, 6 }, = { LCD_RAM_REGISTER2, 10 }, = { LCD_RAM_REGISTER6, 10 },}, = { = { LCD_RAM_REGISTER0, 11 }, = { LCD_RAM_REGISTER0, 12 }, = { LCD_RAM_REGISTER4, 12 }, = { LCD_RAM_REGISTER6, 11 }, = { LCD_RAM_REGISTER4, 11 }, = { LCD_RAM_REGISTER2, 11 }, = { LCD_RAM_REGISTER2, 12 }, = { LCD_RAM_REGISTER6, 12 },}, = { = { LCD_RAM_REGISTER0, 13 }, = { LCD_RAM_REGISTER0, 14 }, = { LCD_RAM_REGISTER4, 14 }, = { LCD_RAM_REGISTER6, 13 }, = { LCD_RAM_REGISTER4, 13 }, = { LCD_RAM_REGISTER2, 13 }, = { LCD_RAM_REGISTER2, 14 },},};void clear_char(char_name_t c){uint16_t mask;for(uint8_t i=0; i<seg_count; i++){mask = 1 << seg_data.mask;HAL_LCD_Write(&hlcd, seg_data.reg, mask, 0 );}HAL_LCD_UpdateDisplayRequest(&hlcd);}// Dp not implementedvoid write_char(char_name_t c, uint8_t number, bool dp){uint16_t mask;if (number>9)number=8;for(uint8_t i=0; i<seg_count; i++){mask = 1 << seg_data.mask;HAL_LCD_Write(&hlcd, seg_data.reg, mask,( ((1<<i) & digits) ? mask : 0 ) );}HAL_LCD_UpdateDisplayRequest(&hlcd);}void main(void){uint8_t a=0, b=0, c=0, d=0;while(1){write_char(char_1, a, false);write_char(char_2, b, false);write_char(char_3, c, false);write_char(char_4, d, false);if(++a>9){a=0;if(++b>9){b=0;if(++c>9){c=0;if(++d>9)d=0;}}}HAL_Delay(1000);}}

author: monthlybasil
author_rank: Newbie
timestamp: March 12, 2024, 09:16:55 am
content: I know its been a while, but I wanted to put this here for others to use, and maybe get some feedback.this is my first try at writing anything in c, I'm very much a beginner, that's probably why it's taken so long.anyway, here's main.c from my project.It might look janky, but it works. and other than some calibration I'll need to do when I'm home with a multimeter, it reports temps.Code:/* USER CODE BEGIN Header *//********************************************************************************* @file : main.c* @brief : Main program body******************************************************************************* @attention** Copyright (c) 2024 STMicroelectronics.* All rights reserved.** This software is licensed under terms that can be found in the LICENSE file* in the root directory of this software component.* If no LICENSE file comes with this software, it is provided AS-IS.********************************************************************************//* USER CODE END Header *//* Includes ------------------------------------------------------------------*/#include "main.h"#include "usb_device.h"/* Private includes ----------------------------------------------------------*//* USER CODE BEGIN Includes */#include "stdio.h"#include "usbd_cdc_if.h"#include <math.h>#include <stdbool.h>#include <stdint.h>/* USER CODE END Includes *//* Private typedef -----------------------------------------------------------*//* USER CODE BEGIN PTD *//* USER CODE END PTD *//* Private define ------------------------------------------------------------*//* USER CODE BEGIN PD */// Steinhart-Hart coefficients#define A_COEFF 0.001125308852122#define B_COEFF 0.000234711863267#define C_COEFF 8.76711446883e-08#define REFERENCE_RESISTANCE 20000.0 // 20 kΩ used for the temperature calculation// Define the number of characters and segments#define char_count 4#define seg_count 7// Define enumerations for segment and character namestypedef enum {seg_a = 0,seg_b,seg_c,seg_d,seg_e,seg_f,seg_g,} seg_name_t;typedef enum {char_1 = 0,char_2,char_3,char_4,} char_name_t;// 2D array to hold segment data for each charactertypedef struct {const uint8_t reg; // LCD RAM register to write data toconst uint16_t mask; // Bit mask for the specific segment within the register} seg_data_t;seg_data_t seg_data = { = { = { LCD_RAM_REGISTER0, 13 }, //0 = { LCD_RAM_REGISTER0, 14 }, //1 = { LCD_RAM_REGISTER4, 14 }, //2 = { LCD_RAM_REGISTER6, 13 }, //3 = { LCD_RAM_REGISTER4, 13 }, //4 = { LCD_RAM_REGISTER2, 13 }, //5 = { LCD_RAM_REGISTER2, 14 }, //6}, = { = { LCD_RAM_REGISTER0, 11 }, = { LCD_RAM_REGISTER0, 12 }, = { LCD_RAM_REGISTER4, 12 }, = { LCD_RAM_REGISTER6, 11 }, = { LCD_RAM_REGISTER4, 11 }, = { LCD_RAM_REGISTER2, 11 }, = { LCD_RAM_REGISTER2, 12 },}, = { = { LCD_RAM_REGISTER0, 6 }, = { LCD_RAM_REGISTER0, 10 }, = { LCD_RAM_REGISTER4, 10 }, = { LCD_RAM_REGISTER6, 6 }, = { LCD_RAM_REGISTER4, 6 }, = { LCD_RAM_REGISTER2, 6 }, = { LCD_RAM_REGISTER2, 10 },}, = { = { LCD_RAM_REGISTER0, 1 }, = { LCD_RAM_REGISTER0, 5 }, = { LCD_RAM_REGISTER4, 5 }, = { LCD_RAM_REGISTER6, 1 }, = { LCD_RAM_REGISTER4, 1 }, = { LCD_RAM_REGISTER2, 1 }, = { LCD_RAM_REGISTER2, 5 },},};const uint8_t SevenSegmentASCII = {0b00000000, /* 0 - */0b00000000, /* 1 - */0b00000000, /* 2 - */0b00000000, /* 3 - */0b00000000, /* 4 - */0b00000000, /*5 - */0b00000000, /*6 - */0b00000000, /*7 - */0b00000000, /*8 - */0b00000000, /* 9 - */0b00000000, /* 10 - */0b00000000, /* 11 - */0b00000000, /* 12 - */0b00000000, /* 13 - */0b00000000, /* 14 - */0b00000000, /* 15 - */0b00000000, /* 16 - */0b00000000, /* 17 - */0b00000000, /* 18 - */0b00000000, /* 19 - */0b00000000, /* 20 - */0b00000000, /* 21 - */0b00000000, /* 22 - */0b00000000, /* 23 - */0b00000000, /* 24 - */0b00000000, /* 25 - */0b00000000, /* 26 - */0b00000000, /* 27 - */0b00000000, /* 28 - */0b00000000, /* 29 - */0b00000000, /* 30 - */0b00000000, /* 31 - */0b00000000, /* 32 - space */0b10000110, /* 33 - ! */0b00100010, /* 34 - " */0b01111110, /* 35 - # */0b01101101, /* 36 - $ */0b11010010, /* 37 - % */0b01000110, /* 38 - & */0b00100000, /* 39 - ' */0b00101001, /* 40 - ( */0b00001011, /* 41 - ) */0b00100001, /* 42 - * */0b01110000, /* 43 - + */0b00010000, /* 44 - , */0b01000000, /* 45 - - */0b10000000, /* 46 - . */0b01010010, /* 47 - / */0b00111111, /* 48 - 0 */0b00000110, /* 49 - 1 */0b01011011, /* 50 - 2 */0b01001111, /* 51 - 3 */0b01100110, /* 52 - 4 */0b01101101, /* 53 - 5 */0b01111101, /* 54 - 6 */0b00000111, /* 55 - 7 */0b01111111, /* 56 - 8 */0b01101111, /* 57 - 9 */0b00001001, /* 58 - : */0b00001101, /* 59 - ; */0b01100001, /* 60 - < */0b01001000, /* 61 - = */0b01000011, /* 62 - > */0b11010011, /* 63 - ? */0b01011111, /* 64 - @ */0b01110111, /* 65 - A */0b01111100, /* 66 - B */0b00111001, /* 67 - C */0b01011110, /* 68 - D */0b01111001, /* 69 - E */0b01110001, /* 70 - F */0b00111101, /* 71 - G */0b01110110, /* 72 - H */0b00110000, /* 73 - I */0b00011110, /* 74 - J */0b01110101, /* 75 - K */0b00111000, /* 76 - L */0b00010101, /* 77 - M */0b00110111, /* 78 - N */0b00111111, /* 79 - O */0b01110011, /* 80 - P */0b01101011, /* 81 - Q */0b00110011, /* 82 - R */0b01101101, /* 83 - S */0b01111000, /* 84 - T */0b00111110, /* 85 - U */0b00111110, /* 86 - V */0b00101010, /* 87 - W */0b01110110, /* 88 - X */0b01101110, /* 89 - Y */0b01011011, /* 90 - Z */0b00111001, /* 91 - [ */0b01100100, /* 92 - \ */0b00001111, /* 93 - ] */0b00100011, /* 94 - ^ */0b00001000, /* 95 - _ */0b00000010, /* 96 - ` */0b01011111, /* 97 - a */0b01111100, /* 98 - b */0b01011000, /* 99 - c */0b01011110, /* 100 - d */0b01111011, /* 101 - e */0b01110001, /* 102 - f */0b01101111, /* 103 - g */0b01110100, /* 104 - h */0b00010000, /* 105 - i */0b00001100, /* 106 - j */0b01110101, /* 107 - k */0b00110000, /* 108 - l */0b00010100, /* 109 - m */0b01010100, /* 110 - n */0b01011100, /* 111 - o */0b01110011, /* 112 - p */0b01100111, /* 113 - q */0b01010000, /* 114 - r */0b01101101, /* 115 - s */0b01111000, /* 116 - t */0b00011100, /* 117 - u */0b00011100, /* 118 - v */0b00010100, /* 119 - w */0b01110110, /* 120 - x */0b01101110, /* 121 - y */0b01011011, /* 122 - z */0b01000110, /* 123 - { */0b00110000, /* 124 - | */0b01110000, /* 125 - } */0b00000001, /* 126 - ~ */0b11111111, /* 127 - del */};/* USER CODE END PD *//* Private macro -------------------------------------------------------------*//* USER CODE BEGIN PM *//* USER CODE END PM *//* Private variables ---------------------------------------------------------*/ADC_HandleTypeDef hadc;LCD_HandleTypeDef hlcd;RTC_HandleTypeDef hrtc;/* USER CODE BEGIN PV */uint32_t adc_value;/* USER CODE END PV *//* Private function prototypes -----------------------------------------------*/void SystemClock_Config(void);static void MX_GPIO_Init(void);static void MX_LCD_Init(void);static void MX_ADC_Init(void);static void MX_RTC_Init(void);/* USER CODE BEGIN PFP */// Main function/* USER CODE END PFP *//* Private user code ---------------------------------------------------------*//* USER CODE BEGIN 0 *//* USER CODE END 0 *//*** @brief The application entry point.* @retval int*/int main(void){/* USER CODE BEGIN 1 *//* USER CODE END 1 *//* MCU Configuration--------------------------------------------------------*//* Reset of all peripherals, Initializes the Flash interface and the Systick. */HAL_Init();/* USER CODE BEGIN Init *//* USER CODE END Init *//* Configure the system clock */SystemClock_Config();/* USER CODE BEGIN SysInit *//* USER CODE END SysInit *//* Initialize all configured peripherals */MX_GPIO_Init();MX_LCD_Init();MX_ADC_Init();MX_RTC_Init();MX_USB_DEVICE_Init();/* USER CODE BEGIN 2 *//* USER CODE END 2 *//* Infinite loop *//* USER CODE BEGIN WHILE */while (1) {/* USER CODE END WHILE *//* USER CODE BEGIN 3 */void init_display(){//All segments display test/*RAM REG1514131211109876543210A0LowBatt1b1a2b2a3b3a4b4aRUNF B2Profile1g1f2g2f3g3f4g4fCROSSG4degC1c1e2c2e3c3e4c4eTICKE C6degF%1d2dp2d3dp3d4dDIAGD dp11111100000000005432109876543210*/HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER0, 0xFC63, 0b1111110001100011);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER2, 0xFC63, 0b1111110001100011);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER4, 0xFC63, 0b1111110001100011);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 0xFC63, 0b0111110001000011);HAL_LCD_UpdateDisplayRequest(&hlcd);HAL_Delay(1000);HAL_LCD_Clear(&hlcd);HAL_Delay(100);}void init_sensors(){//show 'Init' on displayHAL_LCD_Write(&hlcd, LCD_RAM_REGISTER0, 0xFC63, 0x20);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER2, 0xFC63, 0x6400);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER4, 0xFC63, 0x3460);HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 0xFC43, 0x2000);HAL_LCD_UpdateDisplayRequest(&hlcd);//instead of Delay below, change this to calibrate the temp sensor, maybe also show the battery percentage?HAL_Delay(5000);HAL_LCD_Clear(&hlcd);}void DisplayNumber(float number, int unit){ //units not implemented yet// TODO UNITS using LCD symbols, input sanistisation?// Round the number to the desired decimal placesint decimalPlaces = 0;if (number < -999.5){number = -999;decimalPlaces = 0;}else if (-999.5 < number && number < -99.95){decimalPlaces = 0;}else if (-99.95 < number && number < -9.95){decimalPlaces = 1;}else if (-9.95 < number && number < 99.95){decimalPlaces = 2;}else if (99.95 < number && number < 999.95){decimalPlaces = 1;}else if (999.95 < number && number < 9999.5){decimalPlaces = 0;}else if (number > 9999.5){number = 9999;decimalPlaces = 0;}else {number = 0;decimalPlaces = 2;}double roundedNumber = number * pow(10, decimalPlaces);roundedNumber = round(roundedNumber);double unroundedNumber = roundedNumber / pow(10, decimalPlaces);HAL_LCD_Clear(&hlcd);if (decimalPlaces == 2){HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 1 << 10, 1 << 10);}else if (decimalPlaces == 1){HAL_LCD_Write(&hlcd, LCD_RAM_REGISTER6, 1 << 12, 1 << 12);}else;// (no decimal places)for(int c=0; c < char_count; c++){ //For each Character:int digit = (abs((int)(roundedNumber / pow(10, c)))) % 10; // Extract digit at position c//char buffer; // communicate on the USB serial as each digit is written//int len = sprintf(buffer,"number: %f Input: %4.2f, dp: %d char %d, number: %d, ASCII: 0x%2X\r\n", number, unroundedNumber, decimalPlaces, c, digit, SevenSegmentASCII[digit + 48]);//CDC_Transmit_FS((uint8_t *)buffer, len);for(uint8_t s=0; s<seg_count; s++){ //each segment gets writtenint bit = ((SevenSegmentASCII[digit + 48] >> s) & 1); //bitshift to the 's' segment and check if its a 1, (by ANDing segment with 1)if (c == 3 && unroundedNumber < 0){ //is negativebit = ((SevenSegmentASCII >> s) & 1);}else if (c == 3 && 0 <= unroundedNumber && unroundedNumber < 10){//between 0 and 10bit = ((SevenSegmentASCII >> s) & 1);}HAL_LCD_Write(&hlcd, seg_data.reg, 0xFC63, bit << seg_data.mask); //unmask all bits, and write that segments position to the appropriate ram register.}}HAL_LCD_UpdateDisplayRequest(&hlcd);//HAL_Delay(1000);}void get_temp(){//Trigger ADC conversionHAL_ADC_Start(&hadc);if (HAL_ADC_PollForConversion(&hadc, HAL_MAX_DELAY) == HAL_OK) {adc_value = HAL_ADC_GetValue(&hadc);// Convert ADC value to temperature using Steinhart-Hart equation with calibration factorfloat resistance = REFERENCE_RESISTANCE * ((float)adc_value / 4095.0); // Calibration factorfloat temperature_kelvin = 1.0 / (A_COEFF + B_COEFF * log(resistance) + C_COEFF * pow(log(resistance), 3));float temperature_celsius = temperature_kelvin - 273.15;DisplayNumber(temperature_celsius,0);// Prepare the data to be transmitted serial USBchar buffer;int len = sprintf(buffer, "Raw ADC Value: %4lu - Temperature: %.2f\r\n", adc_value, temperature_celsius);//Transmit data through USBCDC_Transmit_FS((uint8_t *)buffer, len);}}//Function to test the DisplayNumber Function with various 'testNumbers' values/*void testFunctionNumbers(){double testNumbers[] = {-999, -99.9, -9.99, -9.01, -1.234, 0, 5.678, 99.99, 999, 9999};int numTests = sizeof(testNumbers) / sizeof(testNumbers);for (int i = 0; i < numTests; i++) {//char buffer;//int len = sprintf(buffer, "Input: %7.2f", testNumbers);//CDC_Transmit_FS((uint8_t *)buffer, len);HAL_LCD_Clear(&hlcd);DisplayNumber(testNumbers,0);HAL_Delay(5000);}}*//*//iterative testvoid testFunctionIterate(){for(double testValue=-1000.01; testValue < 10010; (testValue = testValue + 0.01)){//char buffer;//int len = sprintf(buffer, "Input: %7.2f\r\n", testValue);//CDC_Transmit_FS((uint8_t *)buffer, len);HAL_LCD_Clear(&hlcd);DisplayNumber(testValue,0);HAL_Delay(10);}}*//*//Segment Testvoid testFunctionCharacters(){ // this function doesn't rely on the Display numbers function, it interfaces directly with the display RAM.// This tests the display displaying one digit one each character position.for(int j=0; j < 10; j++){ // count to tenHAL_LCD_Clear(&hlcd);for(int i=0; i < char_count; i++){ //For each Character://char buffer; // communicate on the USB serial as each digit is written//int len = sprintf(buffer, "char %d, number: %d, ASCII: 0x%2X\r\n", i, j, SevenSegmentASCII[j + 48]);//CDC_Transmit_FS((uint8_t *)buffer, len);for(uint8_t k=0; k<seg_count; k++){ //each segment gets writtenint data = ((SevenSegmentASCII[j + 48] >> k) & 1); //bitshift to the 'í' segment and check if its a 1, (by ANDing segment with 1)HAL_LCD_Write(&hlcd, seg_data.reg, 1 << seg_data.mask, data << seg_data.mask); //unmask all bits, and write that segments position to the appropriate ram register.}HAL_LCD_UpdateDisplayRequest(&hlcd);HAL_Delay(1000);}}}*///init_display();//init_sensors(); // not implemented yet//testFunctionCharacters();//testFunctionNumbers();//testFunctionIterate();get_temp();HAL_Delay(500);}/* USER CODE END 3 */}/*** @brief System Clock Configuration* @retval None*/void SystemClock_Config(void){RCC_OscInitTypeDef RCC_OscInitStruct = {0};RCC_ClkInitTypeDef RCC_ClkInitStruct = {0};RCC_PeriphCLKInitTypeDef PeriphClkInit = {0};/** Configure the main internal regulator output voltage*/__HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1);/** Initializes the RCC Oscillators according to the specified parameters* in the RCC_OscInitTypeDef structure.*/RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI|RCC_OSCILLATORTYPE_LSI|RCC_OSCILLATORTYPE_HSI48;RCC_OscInitStruct.HSIState = RCC_HSI_ON;RCC_OscInitStruct.HSICalibrationValue = RCC_HSICALIBRATION_DEFAULT;RCC_OscInitStruct.LSIState = RCC_LSI_ON;RCC_OscInitStruct.HSI48State = RCC_HSI48_ON;RCC_OscInitStruct.PLL.PLLState = RCC_PLL_NONE;if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK){Error_Handler();}/** Initializes the CPU, AHB and APB buses clocks*/RCC_ClkInitStruct.ClockType = RCC_CLOCKTYPE_HCLK|RCC_CLOCKTYPE_SYSCLK|RCC_CLOCKTYPE_PCLK1|RCC_CLOCKTYPE_PCLK2;RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_HSI;RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1;RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV1;RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV1;if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_0) != HAL_OK){Error_Handler();}PeriphClkInit.PeriphClockSelection = RCC_PERIPHCLK_RTC|RCC_PERIPHCLK_USB;PeriphClkInit.RTCClockSelection = RCC_RTCCLKSOURCE_LSI;PeriphClkInit.UsbClockSelection = RCC_USBCLKSOURCE_HSI48;if (HAL_RCCEx_PeriphCLKConfig(&PeriphClkInit) != HAL_OK){Error_Handler();}}/*** @brief ADC Initialization Function* @param None* @retval None*/static void MX_ADC_Init(void){/* USER CODE BEGIN ADC_Init 0 *//* USER CODE END ADC_Init 0 */ADC_ChannelConfTypeDef sConfig = {0};/* USER CODE BEGIN ADC_Init 1 *//* USER CODE END ADC_Init 1 *//** Configure the global features of the ADC (Clock, Resolution, Data Alignment and number of conversion)*/hadc.Instance = ADC1;hadc.Init.OversamplingMode = DISABLE;hadc.Init.ClockPrescaler = ADC_CLOCK_SYNC_PCLK_DIV1;hadc.Init.Resolution = ADC_RESOLUTION_12B;hadc.Init.SamplingTime = ADC_SAMPLETIME_1CYCLE_5;hadc.Init.ScanConvMode = ADC_SCAN_DIRECTION_FORWARD;hadc.Init.DataAlign = ADC_DATAALIGN_RIGHT;hadc.Init.ContinuousConvMode = DISABLE;hadc.Init.DiscontinuousConvMode = DISABLE;hadc.Init.ExternalTrigConvEdge = ADC_EXTERNALTRIGCONVEDGE_NONE;hadc.Init.ExternalTrigConv = ADC_SOFTWARE_START;hadc.Init.DMAContinuousRequests = DISABLE;hadc.Init.EOCSelection = ADC_EOC_SINGLE_CONV;hadc.Init.Overrun = ADC_OVR_DATA_PRESERVED;hadc.Init.LowPowerAutoWait = DISABLE;hadc.Init.LowPowerFrequencyMode = DISABLE;hadc.Init.LowPowerAutoPowerOff = DISABLE;if (HAL_ADC_Init(&hadc) != HAL_OK){Error_Handler();}/** Configure for the selected ADC regular channel to be converted.*/sConfig.Channel = ADC_CHANNEL_5;sConfig.Rank = ADC_RANK_CHANNEL_NUMBER;if (HAL_ADC_ConfigChannel(&hadc, &sConfig) != HAL_OK){Error_Handler();}/* USER CODE BEGIN ADC_Init 2 *//* USER CODE END ADC_Init 2 */}/*** @brief LCD Initialization Function* @param None* @retval None*/static void MX_LCD_Init(void){/* USER CODE BEGIN LCD_Init 0 *//* USER CODE END LCD_Init 0 *//* USER CODE BEGIN LCD_Init 1 *//* USER CODE END LCD_Init 1 */hlcd.Instance = LCD;hlcd.Init.Prescaler = LCD_PRESCALER_1;hlcd.Init.Divider = LCD_DIVIDER_16;hlcd.Init.Duty = LCD_DUTY_1_4;hlcd.Init.Bias = LCD_BIAS_1_4;hlcd.Init.VoltageSource = LCD_VOLTAGESOURCE_INTERNAL;hlcd.Init.Contrast = LCD_CONTRASTLEVEL_3;hlcd.Init.DeadTime = LCD_DEADTIME_0;hlcd.Init.PulseOnDuration = LCD_PULSEONDURATION_4;hlcd.Init.HighDrive = LCD_HIGHDRIVE_0;hlcd.Init.BlinkMode = LCD_BLINKMODE_OFF;hlcd.Init.BlinkFrequency = LCD_BLINKFREQUENCY_DIV8;hlcd.Init.MuxSegment = LCD_MUXSEGMENT_DISABLE;if (HAL_LCD_Init(&hlcd) != HAL_OK){Error_Handler();}/* USER CODE BEGIN LCD_Init 2 *//* USER CODE END LCD_Init 2 */}/*** @brief RTC Initialization Function* @param None* @retval None*/static void MX_RTC_Init(void){/* USER CODE BEGIN RTC_Init 0 *//* USER CODE END RTC_Init 0 */RTC_TimeTypeDef sTime = {0};RTC_DateTypeDef sDate = {0};/* USER CODE BEGIN RTC_Init 1 *//* USER CODE END RTC_Init 1 *//** Initialize RTC Only*/hrtc.Instance = RTC;hrtc.Init.HourFormat = RTC_HOURFORMAT_24;hrtc.Init.AsynchPrediv = 127;hrtc.Init.SynchPrediv = 255;hrtc.Init.OutPut = RTC_OUTPUT_DISABLE;hrtc.Init.OutPutRemap = RTC_OUTPUT_REMAP_NONE;hrtc.Init.OutPutPolarity = RTC_OUTPUT_POLARITY_HIGH;hrtc.Init.OutPutType = RTC_OUTPUT_TYPE_OPENDRAIN;if (HAL_RTC_Init(&hrtc) != HAL_OK){Error_Handler();}/* USER CODE BEGIN Check_RTC_BKUP *//* USER CODE END Check_RTC_BKUP *//** Initialize RTC and set the Time and Date*/sTime.Hours = 21;sTime.Minutes = 35;sTime.Seconds = 0;sTime.DayLightSaving = RTC_DAYLIGHTSAVING_NONE;sTime.StoreOperation = RTC_STOREOPERATION_RESET;if (HAL_RTC_SetTime(&hrtc, &sTime, RTC_FORMAT_BIN) != HAL_OK){Error_Handler();}sDate.WeekDay = RTC_WEEKDAY_MONDAY;sDate.Month = RTC_MONTH_JANUARY;sDate.Date = 29;sDate.Year = 0;if (HAL_RTC_SetDate(&hrtc, &sDate, RTC_FORMAT_BIN) != HAL_OK){Error_Handler();}/* USER CODE BEGIN RTC_Init 2 *//* USER CODE END RTC_Init 2 */}/*** @brief GPIO Initialization Function* @param None* @retval None*/static void MX_GPIO_Init(void){GPIO_InitTypeDef GPIO_InitStruct = {0};/* USER CODE BEGIN MX_GPIO_Init_1 *//* USER CODE END MX_GPIO_Init_1 *//* GPIO Ports Clock Enable */__HAL_RCC_GPIOC_CLK_ENABLE();__HAL_RCC_GPIOH_CLK_ENABLE();__HAL_RCC_GPIOA_CLK_ENABLE();__HAL_RCC_GPIOB_CLK_ENABLE();/*Configure GPIO pin Output Level */HAL_GPIO_WritePin(GPIOA, GPIO_PIN_3, GPIO_PIN_RESET);/*Configure GPIO pin : PH0 */GPIO_InitStruct.Pin = GPIO_PIN_0;GPIO_InitStruct.Mode = GPIO_MODE_INPUT;GPIO_InitStruct.Pull = GPIO_NOPULL;HAL_GPIO_Init(GPIOH, &GPIO_InitStruct);/*Configure GPIO pin : PA3 */GPIO_InitStruct.Pin = GPIO_PIN_3;GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;GPIO_InitStruct.Pull = GPIO_NOPULL;GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);/* USER CODE BEGIN MX_GPIO_Init_2 *//* USER CODE END MX_GPIO_Init_2 */}/* USER CODE BEGIN 4 *//* USER CODE END 4 *//*** @brief This function is executed in case of error occurrence.* @retval None*/void Error_Handler(void){/* USER CODE BEGIN Error_Handler_Debug *//* User can add his own implementation to report the HAL error return state */__disable_irq();while (1){}/* USER CODE END Error_Handler_Debug */}#ifdef USE_FULL_ASSERT/*** @brief Reports the name of the source file and the source line number* where the assert_param error has occurred.* @param file: pointer to the source file name* @param line: assert_param error line source number* @retval None*/void assert_failed(uint8_t *file, uint32_t line){/* USER CODE BEGIN 6 *//* User can add his own implementation to report the file name and line number,ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) *//* USER CODE END 6 */}#endif /* USE_FULL_ASSERT */

author: toumbi
author_rank: Newbie
timestamp: May 20, 2025, 08:12:29 am
content: Hi,I get one used ELPRO LIBERO CS that is used meaning the pdf is generated.I found also if i remove the battery and press the button while connect it to usb , the lcd display bldr meaning bootloader.It should have a way to reflash the logger just by injecting a file.i tried running a dd command on bootloader mode : my device is connected to /dev/disk4:Code:sudo dd if=/dev/disk4 of=dd_dump_dev_disk4_bldr.binhere is the content :Code:xxd -a dd_dump_dev_disk4_bldr.binCode:% xxd -a dd_dump_dev_disk4_bldr.bin00000000: 0000 0000 0000 0000 0000 0000 0000 0000 ................*000001c0: 0100 0100 0404 0100 0000 0001 0000 0000 ................000001d0: 0000 0000 0000 0000 0000 0000 0000 0000 ................000001e0: 0000 0000 0000 0000 0000 0000 0000 0000 ................000001f0: 0000 0000 0000 0000 0000 0000 0000 55aa ..............U.00000200: eb3c 904d 5357 494e 342e 3100 0201 0100 .<.MSWIN4.1.....00000210: 0200 0200 01f0 0100 0100 0100 0000 0000 ................00000220: 0000 0000 8000 2975 326e 0a4c 4942 4552 ......)u2n.LIBER00000230: 4f20 2020 2020 4641 5431 3220 2020 0000 O FAT12 ..00000240: 0000 0000 0000 0000 0000 0000 0000 0000 ................*000003f0: 0000 0000 0000 0000 0000 0000 0000 55aa ..............U.00000400: f0ff ff03 4000 0560 0007 8000 09a0 000b ....@..`........00000410: c000 0df0 ff0f 0001 1120 0113 4001 1560 ......... ..@..`00000420: 0117 8001 19a0 011b c001 1de0 011f 0002 ................00000430: 2120 0223 4002 2560 0227 8002 29a0 022b ! .#@.%`.'..)..+00000440: c002 2de0 022f 0003 3120 0333 4003 3560 ..-../..1 .3@.5`00000450: 0337 8003 39a0 033b c003 3de0 033f 0004 .7..9..;..=..?..00000460: 4120 0443 4004 4560 0447 8004 49a0 044b A .C@.E`.G..I..K00000470: c004 4de0 044f 0005 5120 0553 4005 5560 ..M..O..Q .S@.U`00000480: 0557 8005 59a0 055b c005 5de0 055f 0006 .W..Y..[..].._..00000490: 6120 0663 4006 6560 0667 8006 69a0 066b a .c@.e`.g..i..k000004a0: c006 6de0 066f 0007 7120 0773 4007 7560 ..m..o..q .s@.u`000004b0: 0777 8007 79a0 077b c007 7de0 077f 0008 .w..y..{..}.....000004c0: 8120 0883 4008 8560 0887 8008 89a0 088b . ..@..`........000004d0: c008 8de0 088f 0009 9120 0993 4009 9560 ......... ..@..`000004e0: 0997 8009 99a0 099b c009 9de0 099f 000a ................000004f0: a120 0aa3 400a a560 0aa7 800a a9a0 0aab . ..@..`........00000500: c00a ade0 0aaf 000b b120 0bb3 400b b560 ......... ..@..`00000510: 0bb7 800b b9a0 0bbb c00b bde0 0bbf 000c ................00000520: c120 0cc3 400c c560 0cc7 800c c9a0 0ccb . ..@..`........00000530: c00c cde0 0cff 0f00 0000 0000 0000 0000 ................00000540: 0000 0000 0000 0000 0000 0000 0000 0000 ................*00000600: f0ff ff03 4000 0560 0007 8000 09a0 000b ....@..`........00000610: c000 0df0 ff0f 0001 1120 0113 4001 1560 ......... ..@..`00000620: 0117 8001 19a0 011b c001 1de0 011f 0002 ................00000630: 2120 0223 4002 2560 0227 8002 29a0 022b ! .#@.%`.'..)..+00000640: c002 2de0 022f 0003 3120 0333 4003 3560 ..-../..1 .3@.5`00000650: 0337 8003 39a0 033b c003 3de0 033f 0004 .7..9..;..=..?..00000660: 4120 0443 4004 4560 0447 8004 49a0 044b A .C@.E`.G..I..K00000670: c004 4de0 044f 0005 5120 0553 4005 5560 ..M..O..Q .S@.U`00000680: 0557 8005 59a0 055b c005 5de0 055f 0006 .W..Y..[..].._..00000690: 6120 0663 4006 6560 0667 8006 69a0 066b a .c@.e`.g..i..k000006a0: c006 6de0 066f 0007 7120 0773 4007 7560 ..m..o..q .s@.u`000006b0: 0777 8007 79a0 077b c007 7de0 077f 0008 .w..y..{..}.....000006c0: 8120 0883 4008 8560 0887 8008 89a0 088b . ..@..`........000006d0: c008 8de0 088f 0009 9120 0993 4009 9560 ......... ..@..`000006e0: 0997 8009 99a0 099b c009 9de0 099f 000a ................000006f0: a120 0aa3 400a a560 0aa7 800a a9a0 0aab . ..@..`........00000700: c00a ade0 0aaf 000b b120 0bb3 400b b560 ......... ..@..`00000710: 0bb7 800b b9a0 0bbb c00b bde0 0bbf 000c ................00000720: c120 0cc3 400c c560 0cc7 800c c9a0 0ccb . ..@..`........00000730: c00c cde0 0cff 0f00 0000 0000 0000 0000 ................00000740: 0000 0000 0000 0000 0000 0000 0000 0000 ................*00000800: 4c49 4245 524f 5f4c 4452 2008 0000 0000 LIBERO_LDR .....00000810: 0000 0000 0000 7dbf 9f01 0000 0000 0000 ......}.........00000820: 4544 5820 2020 2020 4946 2026 0000 7dbf EDX IF &..}.00000830: 9f01 0000 0000 7dbf 9f01 0200 0018 0000 ......}.........00000840: 4c49 4245 524f 2020 4441 5426 0000 7dbf LIBERO DAT&..}.00000850: 9f01 0000 0000 7dbf 9f01 0e00 0082 0100 ......}.........00000860: 0000 0000 0000 0000 0000 0000 0000 0000 ................*00004800: 426f 6f74 6c6f 6164 6572 0d0a 5549 443a Bootloader..UID:00004810: 2030 3032 3730 3034 3133 3033 3633 3533 00270041303635300004820: 3330 4134 3733 3233 340d 0a52 4556 4944 30A473234..REVID00004830: 3a20 3230 3038 0d0a 4669 726d 7761 7265 : 2008..Firmware00004840: 3a20 5630 2e32 3020 636f 6d70 696c 6564 : V0.20 compiled00004850: 204a 616e 2020 3620 3230 3232 2031 363a Jan 6 2022 16:00004860: 3233 3a35 330d 0a43 6f6d 7069 6c65 723a 23:53..Compiler:00004870: 2038 3035 3030 3039 0d0a 0d0a 3e20 5265 8050009....> Re00004880: 6164 790d 0a00 0000 0000 0000 0000 0000 ady.............00004890: 0000 0000 0000 0000 0000 0000 0000 0000 ................*0001fff0: 0000 0000 0000 0000 0000 0000 0000 0000 ................it's possible we can access part of the firmware on this extract data ?