diff --git a/target/linux/lantiq/image/Makefile b/target/linux/lantiq/image/Makefile index f8d46fb94e..e2a72b238f 100644 --- a/target/linux/lantiq/image/Makefile +++ b/target/linux/lantiq/image/Makefile @@ -83,6 +83,43 @@ define Image/Build/squashfs $(if $(3),$(call MkBrnImage,$(3),$(4),$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(3)-brnImage,$(2),$(1),$(5))) endef +DGN3500_SKERNEL=0x50000 +DGN3500_SKERNEL_DECIMAL=327680 +define Image/BuildDGN3500/squashfs + dd if=/dev/zero of=$(BIN_DIR)/$(IMG_PREFIX)-pad bs=$(DGN3500_SKERNEL_DECIMAL) count=1 + cat $(BIN_DIR)/$(IMG_PREFIX)-pad $(KDIR)/uImage-$(2) $(KDIR)/root.$(1) > $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img + rm -r $(BIN_DIR)/$(IMG_PREFIX)-pad + dd if=/dev/zero ibs=16M count=1 | tr "\000" "\377" > $(BIN_DIR)/$(IMG_PREFIX)-pwf + cp $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img + dgn3500sum $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img $(DGN3500_SKERNEL) NA + $(call prepare_generic_squashfs,$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img) + cp $(BIN_DIR)/$(IMG_PREFIX)-pwf $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-NA.img + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-NA.img conv=notrunc + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-sysupgrade-NA.image bs=$(DGN3500_SKERNEL_DECIMAL) skip=1 + rm -r $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadNA.img + mv $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img + dgn3500sum $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img $(DGN3500_SKERNEL) WW + $(call prepare_generic_squashfs,$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img) + mv $(BIN_DIR)/$(IMG_PREFIX)-pwf $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-WW.img + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-WW.img conv=notrunc + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-sysupgrade-WW.image bs=$(DGN3500_SKERNEL_DECIMAL) skip=1 + rm -r $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepadWW.img +endef + +define Image/BuildDGN3500B/squashfs + dd if=/dev/zero of=$(BIN_DIR)/$(IMG_PREFIX)-pad bs=327680 count=1 + cat $(BIN_DIR)/$(IMG_PREFIX)-pad $(KDIR)/uImage-$(2) $(KDIR)/root.$(1) > $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img + rm -r $(BIN_DIR)/$(IMG_PREFIX)-pad + dd if=/dev/zero ibs=16M count=1 | tr "\000" "\377" > $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory.img + dgn3500sum $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img $(DGN3500_SKERNEL) DE + $(call prepare_generic_squashfs,$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img) + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory.img conv=notrunc + dd if=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img of=$(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-sysupgrade.image bs=$(DGN3500_SKERNEL_DECIMAL) skip=1 + rm -r $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-factory-prepad.img + dgn3500sum $(BIN_DIR)/$(IMG_PREFIX)-$(2)-$(1)-sysupgrade.image $(DGN3500_SKERNEL) DE +endef + + define Image/BuildTPLink/squashfs mktplinkfw2 -B $(3) -s -a 0x4 -j \ -k $(KDIR)/vmlinux-$(2).lzma -r $(KDIR)/root.$(1) \ @@ -316,10 +353,10 @@ Image/Build/Profile/GIGASX76X=$(call Image/Build/$(1),$(1),GIGASX76X) # AR9 Image/BuildKernel/Profile/DGN3500=$(call Image/BuildKernel/Template,DGN3500) -Image/Build/Profile/DGN3500=$(call Image/Build/$(1),$(1),DGN3500) +Image/Build/Profile/DGN3500=$(call Image/BuildDGN3500/$(1),$(1),DGN3500) -Image/BuildKernel/Profile/DGN3500B=$(call Image/BuildKernel/Template,DGN3500) -Image/Build/Profile/DGN3500B=$(call Image/Build/$(1),$(1),DGN3500) +Image/BuildKernel/Profile/DGN3500B=$(call Image/BuildKernel/Template,DGN3500B) +Image/Build/Profile/DGN3500B=$(call Image/BuildDGN3500B/$(1),$(1),DGN3500B) Image/BuildKernel/Profile/WBMRA=$(call Image/BuildKernel/Template,WBMR) Image/Build/Profile/WBMRA=$(call Image/Build/$(1),$(1),WBMR) diff --git a/tools/firmware-utils/Makefile b/tools/firmware-utils/Makefile index 8f17c3e923..64eccdd226 100644 --- a/tools/firmware-utils/Makefile +++ b/tools/firmware-utils/Makefile @@ -68,6 +68,7 @@ define Host/Compile $(call cc,mkdcs932, -Wall) $(call cc,mkheader_gemtek,-lz) $(call cc,mkrtn56uimg, -lz) + $(call cc,dgn3500sum) endef define Host/Install diff --git a/tools/firmware-utils/src/dgn3500sum.c b/tools/firmware-utils/src/dgn3500sum.c new file mode 100644 index 0000000000..00a0c5f837 --- /dev/null +++ b/tools/firmware-utils/src/dgn3500sum.c @@ -0,0 +1,167 @@ +/* ************************************************************************** + + This program creates a modified 16bit checksum used for the Netgear + DGN3500 series routers. The difference between this and a standard + checksum is that every 0x100 bytes added 0x100 have to be subtracted + from the sum. + + (C) 2013 Marco Antonio Mauro + + Based on previous unattributed work. + + This program is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + This program is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + + ************************************************************************* */ + + +#include +#include +#include +#include + +unsigned char PidDataWW[70] = +{ + 0x73, 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, 0x00, 0x00, 0x00, 0x00, 0x59, 0x50, 0x35, 0x37, 0x32, + 0x33, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x41, 0x00, 0x37, + 0x32, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x73, + 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, +} ; + +unsigned char PidDataDE[70] = +{ + 0x73, 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, 0x00, 0x00, 0x00, 0x00, 0x59, 0x50, 0x35, 0x37, 0x32, + 0x34, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x42, 0x00, 0x37, + 0x32, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x73, + 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, +} ; + +unsigned char PidDataNA[70] = +{ + 0x73, 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, 0x00, 0x00, 0x00, 0x00, 0x59, 0x50, 0x35, 0x37, 0x32, + 0x36, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x41, 0x00, 0x37, + 0x32, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x73, + 0x45, 0x72, 0x43, 0x6F, 0x4D, 0x6D, +} ; + +/* ******************************************************************* + Reads the file into memory and returns pointer to the buffer. */ +static char *readfile(char *filename, int *size) +{ + FILE *fp; + char *buffer; + struct stat info; + + if (stat(filename,&info)!=0) + return NULL; + + if ((fp=fopen(filename,"r"))==NULL) + return NULL; + + buffer=NULL; + for (;;) + { + if ((buffer=(char *)malloc(info.st_size+1))==NULL) + break; + + if (fread(buffer,1,info.st_size,fp)!=info.st_size) + { + free(buffer); + buffer=NULL; + break; + } + + buffer[info.st_size]='\0'; + if(size) *size = info.st_size; + + break; + } + + (void)fclose(fp); + + return buffer; +} + + +/* ******************************************************************* */ +int main(int argc, char** argv) +{ + unsigned long start, i; + char *endptr, *buffer, *p; + int count; // size of file in bytes + unsigned short sum, sum1; + char sumbuf[9]; + + if(argc < 3) { + printf("ERROR: Argument missing!\n\nUsage %s filename starting offset in hex [PID code]\n\n", argv[0]); + return 1; + } + + + FILE *fp = fopen(argv[1], "a"); + if(!fp) { + printf("ERROR: File not writeable!\n"); + return 1; + } + if(argc = 4) + { + printf("%s: PID type: %s\n", argv[0], argv[3]); + if(strcmp(argv[3], "DE")==0) + fwrite(PidDataDE, sizeof(PidDataDE), sizeof(char), fp); /* write DE pid */ + else if(strcmp(argv[3], "NA")==0) + fwrite(PidDataNA, sizeof(PidDataNA), sizeof(char), fp); /* write NA pid */ + else /* if(strcmp(argv[3], "WW")) */ + fwrite(PidDataWW, sizeof(PidDataWW), sizeof(char), fp); /* write WW pid */ + } + else + fwrite(PidDataWW, sizeof(PidDataWW), sizeof(char), fp); /* write WW pid if unspecified */ + + fclose(fp); + + /* Read the file to calculate the checksums */ + buffer = readfile(argv[1], &count); + if(!buffer) { + printf("ERROR: File %s not found!\n", argv[1]); + return 1; + } + + p = buffer; + for(i = 0; i < count; i++) + { + sum += p[i]; + } + + start = strtol(argv[2], &endptr, 16); + p = buffer+start; + sum1 = 0; + for(i = 0; i < count - start; i++) + { + sum1 += p[i]; + } + + sprintf(sumbuf,"%04X%04X",sum1,sum); + /* Append the 2 checksums to end of file */ + fp = fopen(argv[1], "a"); + if(!fp) { + printf("ERROR: File not writeable!\n"); + return 1; + } + fwrite(sumbuf, 8, sizeof(char), fp); + fclose(fp); + free(buffer); + return 0; +}