Another larger update, to handle the CM5, 500, and CM5 Lite. I also replaced the code in the original post, for those who don't look this far.
Code:
/* A C program to decode the pi revision string *//* 20250131 - revised to include CM5, 500, CM5 Lite *//* 20250113 - revised to include 16GB *//* 20231019 - revised to include the 5 *//* 20230629 - revised to include the CM4S *//* 20211028 - revised to include the Zero 2 W *//* 20201103 - revised to include the CM4 and the 400, and 8GB */ #include <stdio.h>#include <stdlib.h>#include <string.h> struct rev_data {int F_flag;int MMM_memory;int CCCC_manufacturer;int PPPP_processor;int TTTTTTTT_type;int RRRR_revision;char *MMM_memory_str;char *CCCC_manufacturer_str;char *PPPP_processor_str;char *TTTTTTTT_type_str;char *RRRR_revision_str;}; void old_style(int code, struct rev_data *rd) {rd->PPPP_processor_str= "BCM2835";switch (code) {case 2 :case 3 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Egoman"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "1.0";break;case 4 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 5 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Qisda"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 6 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Egoman"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 7 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Egoman"; rd->TTTTTTTT_type_str= "A";rd->RRRR_revision_str= "2.0";break;case 8 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "A";rd->RRRR_revision_str= "2.0";break;case 9 :rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Qisda"; rd->TTTTTTTT_type_str= "A";rd->RRRR_revision_str= "2.0";break;case 0x0d:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Egoman"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 0x0e:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 0x0f:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Egoman"; rd->TTTTTTTT_type_str= "B";rd->RRRR_revision_str= "2.0";break;case 0x10:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "B+";rd->RRRR_revision_str= "1.2";break;case 0x11:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "CM1";rd->RRRR_revision_str= "1.0";break;case 0x12:rd->MMM_memory_str= "256MB";rd->CCCC_manufacturer_str= "Sony UK"; rd->TTTTTTTT_type_str= "A+";rd->RRRR_revision_str= "1.1";break;case 0x13:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Embest"; rd->TTTTTTTT_type_str= "B+";rd->RRRR_revision_str= "1.2";break;case 0x14:rd->MMM_memory_str= "512MB";rd->CCCC_manufacturer_str= "Embest"; rd->TTTTTTTT_type_str= "CM1";rd->RRRR_revision_str= "1.0";break;case 0x15:rd->MMM_memory_str= "256MB/512MB";rd->CCCC_manufacturer_str= "Embest"; rd->TTTTTTTT_type_str= "A+";rd->RRRR_revision_str= "1.1";break;}}void new_style(int code, struct rev_data *rd) {rd->MMM_memory= ( code & 0x00700000 ) >> 20;rd->CCCC_manufacturer= ( code & 0x000f0000 ) >> 16;rd->PPPP_processor= ( code & 0x0000f000 ) >> 12;rd->TTTTTTTT_type= ( code & 0x00000ff0 ) >> 4;rd->RRRR_revision= ( code & 0x0000000f ) >> 0;switch (rd->MMM_memory) {case 0 : rd->MMM_memory_str = "256MB"; break;case 1 : rd->MMM_memory_str = "512MB"; break;case 2 : rd->MMM_memory_str = "1GB"; break;case 3 : rd->MMM_memory_str = "2GB"; break;case 4 : rd->MMM_memory_str = "4GB"; break;case 5 : rd->MMM_memory_str = "8GB"; break;case 6 : rd->MMM_memory_str = "16GB"; break;default : rd->MMM_memory_str = "UNKNOWN"; }switch (rd->CCCC_manufacturer) {case 0 : rd->CCCC_manufacturer_str = "Sony UK"; break;case 1 : rd->CCCC_manufacturer_str = "Egoman"; break;case 2 : rd->CCCC_manufacturer_str = "Embest"; break;case 3 : rd->CCCC_manufacturer_str = "Sony Japan"; break;case 4 : rd->CCCC_manufacturer_str = "Embest"; break;case 5 : rd->CCCC_manufacturer_str = "Stadium"; break;default : rd->CCCC_manufacturer_str = "UNKNOWN"; }switch (rd->PPPP_processor) {case 0 : rd->PPPP_processor_str = "BCM2835"; break;case 1 : rd->PPPP_processor_str = "BCM2836"; break;case 2 : rd->PPPP_processor_str = "BCM2837"; break;case 3 : rd->PPPP_processor_str = "BCM2711"; break;case 4 : rd->PPPP_processor_str = "BCM2712"; break;default : rd->PPPP_processor_str = "UNKNOWN"; }switch (rd->TTTTTTTT_type) {case 0 : rd->TTTTTTTT_type_str = "A"; break;case 1 : rd->TTTTTTTT_type_str = "B"; break;case 2 : rd->TTTTTTTT_type_str = "A+"; break;case 3 : rd->TTTTTTTT_type_str = "B+"; break;case 4 : rd->TTTTTTTT_type_str = "2B"; break;case 5 : rd->TTTTTTTT_type_str = "Alpha (early prototype)"; break;case 6 : rd->TTTTTTTT_type_str = "CM1"; break;case 8 : rd->TTTTTTTT_type_str = "3B"; break;case 9 : rd->TTTTTTTT_type_str = "Zero"; break;case 0xa : rd->TTTTTTTT_type_str = "CM3"; break;case 0xc : rd->TTTTTTTT_type_str = "Zero W"; break;case 0xd : rd->TTTTTTTT_type_str = "3B+"; break;case 0xe : rd->TTTTTTTT_type_str = "3A+"; break;case 0xf : rd->TTTTTTTT_type_str = "Internal use only"; break;case 0x10: rd->TTTTTTTT_type_str = "CM3+"; break;case 0x11: rd->TTTTTTTT_type_str = "4B"; break;case 0x12: rd->TTTTTTTT_type_str = "Zero 2 W"; break;case 0x13: rd->TTTTTTTT_type_str = "400"; break;case 0x14: rd->TTTTTTTT_type_str = "CM4"; break;case 0x15: rd->TTTTTTTT_type_str = "CM4S"; break;case 0x16: rd->TTTTTTTT_type_str = "Internal use only"; break;case 0x17: rd->TTTTTTTT_type_str = "5"; break;case 0x18: rd->TTTTTTTT_type_str = "CM5"; break;case 0x19: rd->TTTTTTTT_type_str = "500"; break;case 0x1a: rd->TTTTTTTT_type_str = "CM5 Lite"; break;default : rd->TTTTTTTT_type_str = "UNKNOWN"; }sprintf(rd->RRRR_revision_str, "1.%d", rd->RRRR_revision);}int main(int argc, char* argv[]){char*filename; FILE*fp;ssize_tread = 0;char*line = NULL;size_tlen = 0;intcode = 0;char temp_revision_str[32];struct rev_data rd_null = {0,0,0,0,0,0,NULL,NULL,NULL,NULL,temp_revision_str};if ( argc>1 ) {filename = argv[1];//printf("there is a command-line argument\n");//printf("filename: %s\n", filename);if (strcmp(filename,"-") == 0 ) {//printf("It is a dash\n");fp = stdin;}else {//printf("It is not a dash\n");fp = fopen(filename, "r");if ( fp == NULL ) {printf("open failed\n");exit (1);}//else//printf("open succeeded\n");}}else {//printf("there is NOT any command-line argument\n");fp = stdin;}printf("%s%s%s%s%s%s\n", "Code", "Model", "Proc", "Rev", "RAM", "Manufacturer");while ((read = getline(&line, &len, fp)) != -1) {//printf("Retrieved line of length %zu:\n", read);//printf("%s", line);if ( !sscanf(line, "%x", &code) ) {printf("sscanf failed\n");exit (2);}//printf("code (dec): %d\n", code);//printf("code (hex): %x\n", code);struct rev_data rd = rd_null;rd.F_flag = ( code & 0x00800000 ) >> 23;if ( rd.F_flag == 0 )old_style(code,&rd); else new_style(code,&rd); //printf("F_flag: %x \n", rd.F_flag);//printf("MMM_memory: %x %s \n", rd.MMM_memory, rd.MMM_memory_str);//printf("CCCC_manufacturer : %x %s \n", rd.CCCC_manufacturer, rd.CCCC_manufacturer_str);//printf("PPPP_processor: %x %s \n", rd.PPPP_processor, rd.PPPP_processor_str);//printf("TTTTTTTT_type: %x %s\n", rd.TTTTTTTT_type, rd.TTTTTTTT_type_str);//printf("RRRR_revision: %x \n", rd.RRRR_revision); printf("%04x%s%s%s%s%s\n", code, rd.TTTTTTTT_type_str, rd.PPPP_processor_str, rd.RRRR_revision_str, rd.MMM_memory_str, rd.CCCC_manufacturer_str);}fclose(fp);free(line);}
Statistics: Posted by tinker2much — Sat Feb 01, 2025 12:24 am