| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166 |
- package main
- import (
- "encoding/binary"
- "encoding/hex"
- "fmt"
- "hash/crc32"
- "io"
- "io/ioutil"
- "os"
- "path/filepath"
- "github.com/akamensky/argparse"
- )
- func swab16(x uint16) uint16 {
- return (x&0x00ff)<<8 | (x&0xff00)>>8
- }
- func swab32(x uint32) uint32 {
- return (x&0x000000ff)<<24 | (x&0x0000ff00)<<8 | (x&0x00ff0000)>>8 | (x&0xff000000)>>24
- }
- func sumArr(arr []uint8) uint32 {
- sum := uint32(0)
- for _, val := range arr {
- sum += uint32(val)
- }
- return sum
- }
- func calChecknum(_type string, datas []byte) uint32 {
- if _type == "sum32" {
- return sumArr(datas)
- } else if _type == "crc32" {
- return crc32.ChecksumIEEE(datas)
- } else {
- print("unKown type: " + _type)
- return 0
- }
- }
- func getFileSize(filename string) (int64, error) {
- fileinfo, err := os.Stat(filename)
- if err != nil {
- return 0, err
- }
- size := fileinfo.Size()
- return size, nil
- }
- func ReadBinFile(_name string, _type string, _en string, _block int) {
- FileName := filepath.Base(_name)
- // FileType := filepath.Ext(_name)
- InputFilePath := _name
- OutputFilePath := FileName + "." + _type
- inputFile, err := os.Open(InputFilePath)
- if err != nil {
- panic(err)
- }
- defer inputFile.Close()
- outputFile, err := os.OpenFile(OutputFilePath, os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0644)
- if err != nil {
- panic(err)
- }
- defer outputFile.Close()
- if _block > 0 {
- buffer := make([]byte, _block)
- for {
- n, err := inputFile.Read(buffer)
- if n > 0 {
- // 计算分片的校验和
- check := calChecknum(_type, buffer[:n])
- // 写入分片内容+分片校验和
- if _en == "big" {
- binary.Write(outputFile, binary.BigEndian, buffer[:n])
- binary.Write(outputFile, binary.BigEndian, check)
- } else {
- binary.Write(outputFile, binary.LittleEndian, buffer[:n])
- binary.Write(outputFile, binary.LittleEndian, check)
- }
- }
- if err != nil {
- if err == io.EOF {
- break // 文件读取完毕
- }
- panic(err)
- }
- }
- } else {
- data, err := ioutil.ReadAll(inputFile)
- if err != nil {
- panic(err)
- }
- // 写入全部内容
- if _en == "big" {
- binary.Write(outputFile, binary.BigEndian, data)
- } else {
- binary.Write(outputFile, binary.LittleEndian, data)
- }
- }
- // 读取文件内容到字节切片
- inputFile, err = os.Open(InputFilePath)
- if err != nil {
- panic(err)
- }
- defer inputFile.Close()
- data, err := ioutil.ReadAll(inputFile)
- if err != nil {
- panic(err)
- }
- check := calChecknum(_type, data[:])
- // 写入源文件校验码
- if _en == "big" {
- binary.Write(outputFile, binary.BigEndian, check)
- } else {
- binary.Write(outputFile, binary.LittleEndian, check)
- }
- // 大小端转换
- var networkBytes [4]byte
- if _en == "big" {
- binary.BigEndian.PutUint32(networkBytes[:], check)
- } else {
- binary.LittleEndian.PutUint32(networkBytes[:], check)
- }
- check_hex := hex.EncodeToString(networkBytes[:])
- // 打印输出内容
- size, err := getFileSize(InputFilePath)
- fmt.Println(InputFilePath, fmt.Sprintf("%d", size), _type, check_hex)
- // 关闭文件
- err = outputFile.Close()
- if err != nil {
- fmt.Println(err)
- }
- // 重命名文件
- out_name1 := FileName + "." + _type + "[" + check_hex + "]"
- err = os.Rename(OutputFilePath, out_name1)
- if err != nil {
- fmt.Println("重命名文件出错:", err)
- return
- }
- }
- func main() {
- parser := argparse.NewParser("goChecknum", "这是一个用于固件校验码工具, 制作升级文件")
- _name := parser.String("n", "name", &argparse.Options{Required: true, Help: "bin文件名, 譬如 test.bin", Default: "test.bin"})
- _type := parser.String("t", "type", &argparse.Options{Required: false, Help: "校验方式: sum32,crc32", Default: "sum32"})
- _en := parser.String("e", "en", &argparse.Options{Required: false, Help: "校验码大小端: little,big", Default: "little"})
- _section := parser.Int("s", "section", &argparse.Options{Required: false, Help: "分块大小: 0,1024,2048", Default: 0})
- err := parser.Parse(os.Args)
- if err != nil {
- fmt.Print(parser.Usage(err)) // 帮助 -h or --help
- return
- }
- ReadBinFile(*_name, *_type, *_en, *_section)
- }
|