12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879 |
- #!/usr/bin/perl
- use strict;
- use integer;
- use Digest::CRC;
- my $MAX_DATA_LEN = 16 << 20;
- my $SPIFLASH_MAGIC = 0xe301e7eb;
- sub getint($) {
- my($s) = @_;
- return ($s =~ /^0/) ? oct $s : $s+0;
- }
- sub filelen($) {
- my($f) = @_;
- my @s = stat($f);
- return $s[7];
- }
- sub makeheader($$$$$) {
- my($target,$zlen,$dlen,$dcrc,$address) = @_;
- my $hdr = pack("V*", $SPIFLASH_MAGIC, $zlen, $dlen, $dcrc, $address);
- $hdr .= substr($target.("\0" x 8), 0, 8);
- $hdr .= pack("V", Digest::CRC::crc32($hdr));
- return $hdr;
- }
- my $target = shift @ARGV;
- my $outfile = shift @ARGV;
- if (!defined($outfile)) {
- die "Usage: $0 target_name outfile [infile addr]...\n";
- }
- open(my $out, '>', $outfile)
- or die "$0: $outfile: $!\n";
- binmode($outfile);
- my $err;
- while (1) {
- my $infile = shift @ARGV;
- my $inaddr = getint(shift @ARGV);
- last if (!defined($infile));
- my $in;
- if (!open($in, '<', $infile)) {
- $err = "$infile: $!";
- last;
- }
- binmode($in);
- my $data;
- my $zlen = read($in, $data, $MAX_DATA_LEN);
- close($in);
- my $dlen = $zlen;
- if (substr($in, 0, 3) == "\37\213\10") {
- # gzip file
- $dlen = unpack("V", substr($data, -4));
- }
- my $dcrc = Digest::CRC::crc32($data);
- print $out makeheader($target, $zlen, $dlen, $dcrc, $inaddr);
- print $out $data;
- if ($zlen & 3) {
- # pad to dword boundary
- print $out "\0" x ((4-$zlen) & 3);
- }
- }
- if (defined($err)) {
- close($out);
- unlink($outfile);
- die "$0: $err\n";
- }
- print $out makeheader($target, 0, 0, Digest::CRC::crc32(''), 0);
- close($out);
|