Creating dump header for IBM systems

-Adding dump header script:
-Changes are related to IBM specific systems only, no
impact on the existing dump package format without
dump header. In package function only for IBM systems
the generated header will be added to the dump, for
remaining systems the existing dump format remains same.
-Adding dump header which will be added on top of the
the <obmc file>.tar.xz, only on IBM systems

Note: If user wants to extract the dump, they need to remove
the header from the dump using dd command.
Example
dd bs=628 skip=1 if=<input_dump_file> of=<output_file>

Result:
Tested the dump header using busctl command and dreport script.
Able to add dump header on top of the <obmcdump>.tar.xz file.

Separated out the header from the output file using dd command:
dd bs=628 skip=1 if=<obmc dump>.tar.xz of=openbmc.tar.xz

The new output file doesn't have the header now and can be unzipped.
Post unzipping the files in the dump can be seen.

hexdump ooutput of the dump header:-
00000000  46 49 4c 45 20 20 20 20  00 40 00 00 00 00 00 00  |FILE    .@......|
00000010  00 00 00 00 00 01 00 0f  42 4d 50 44 55 4d 50 2e  |........BMPDUMP.|
00000020  53 49 4d 50 31 30 52 2e  30 30 30 30 30 30 30 36  |SIMP10R.00000006|
00000030  2e 32 30 32 30 30 39 32  39 31 31 31 30 34 33 00  |.20200929111043.|
00000040  53 45 43 54 49 4f 4e 20  00 30 00 00 00 00 00 00  |SECTION .0......|
00000050  00 00 00 01 00 02 00 00  00 00 00 00 00 02 ad dc  |................|
00000060  42 4d 43 44 55 4d 50 00  00 00 00 00 00 00 00 00  |BMCDUMP.........|
00000070  42 4d 43 20 44 55 4d 50  00 00 00 00 00 00 00 00  |BMC DUMP........|
00000080  00 00 00 00 02 10 02 00  00 00 00 00 00 02 ad dc  |................|
00000090  39 31 30 35 2d 32 32 41  00 00 00 00 00 00 00 00  |9105-22A........|
000000a0  00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00  |................|
000000b0  53 65 72 76 65 72 2d 39  31 30 35 2d 32 32 41 2d  |Server-9105-22A-|
000000c0  53 4e 2d 53 49 4d 50 31  30 52 00 00 00 00 00 00  |SN-SIMP10R......|
000000d0  00 53 49 4d 50 31 30 52  00 00 00 00 00 70 00 00  |.SIMP10R.....p..|
000000e0  00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00  |................|
*
00000270  01 01 00 00 fd 37 7a 58  5a 00 00 04 e6 d6 b4 46  |.....7zXZ......F|

Signed-off-by: Chirag Sharma <chirshar@in.ibm.com>
Change-Id: I27bffdd96a6da0777d88e3c7f93eee92cffbfd6e
diff --git a/tools/dreport.d/dreport b/tools/dreport.d/dreport
index 165e11e..d831191 100755
--- a/tools/dreport.d/dreport
+++ b/tools/dreport.d/dreport
@@ -54,6 +54,7 @@
 declare -rx DREPORT_INCLUDE="$DREPORT_SOURCE/include.d"
 declare -rx ZERO="0"
 declare -rx JOURNAL_LINE_LIMIT="500"
+declare -rx HEADER_EXTENSION="$DREPORT_INCLUDE/gendumpheader"
 
 #Error Codes
 declare -rx SUCCESS="0"
@@ -224,8 +225,17 @@
     fi
 
     #tar and compress the files.
-    tar -Jcf "$name_dir.tar.xz" -C \
-             $(dirname "$name_dir") $(basename "$name_dir")
+    if [ -f "$HEADER_EXTENSION" ]; then
+        tar -Jcf "$name_dir.tar.xz" -C \
+                 $(dirname "$name_dir") $(basename "$name_dir")
+        echo "Adding Dump Header :"$HEADER_EXTENSION
+        ("$HEADER_EXTENSION")
+        cat "$name_dir.tar.xz" | tee -a "/tmp/dumpheader_$EPOCHTIME" > /dev/null
+        mv "/tmp/dumpheader_$EPOCHTIME" "$name_dir.tar.xz"
+    else
+        tar -Jcf "$name_dir.tar.xz" -C \
+                 $(dirname "$name_dir") $(basename "$name_dir")
+    fi
 
     if [ $? -ne 0 ]; then
         echo $($TIME_STAMP) "Could not create the compressed tar file"
diff --git a/tools/dreport.d/ibm.d/gendumpheader b/tools/dreport.d/ibm.d/gendumpheader
new file mode 100755
index 0000000..638cf6d
--- /dev/null
+++ b/tools/dreport.d/ibm.d/gendumpheader
@@ -0,0 +1,199 @@
+#!/bin/bash
+#
+#Header for BMC DUMP
+#This script will create header file only for IBM systems.
+#This script will generate generic IBM dump header format.
+#
+#Note: The dump header will be imposed on the dump file i.e
+#<obmdump file>.tar.xz only on IBM specific systems, user needs to
+#separate out the header before extracting the dump.
+#
+
+#Constants
+declare -rx INVENTORY_MANAGER='xyz.openbmc_project.Inventory.Manager'
+declare -rx INVENTORY_PATH='/xyz/openbmc_project/inventory/system'
+declare -rx INVENTORY_ASSET_INT='xyz.openbmc_project.Inventory.Decorator.Asset'
+declare -rx DUMP_HEADER_ENTRY_SIZE='516'
+
+#Variables
+declare -x FILE="/tmp/dumpheader_$EPOCHTIME"
+declare -x dumpSize=$(ls -al $name_dir.tar.xz | awk '{print $5}')
+declare -x modelNo=$(busctl get-property $INVENTORY_MANAGER $INVENTORY_PATH \
+$INVENTORY_ASSET_INT Model | cut -d " " -f 2 | sed "s/^\(\"\)\(.*\)\1\$/\2/g")
+
+declare -x serialNo=$(busctl get-property $INVENTORY_MANAGER $INVENTORY_PATH \
+$INVENTORY_ASSET_INT SerialNumber | cut -d " " -f 2 | sed "s/^\(\"\)\(.*\)\1\$/\2/g")
+
+declare -x dDay=$(date -d @$EPOCHTIME +'%Y%m%d%H%M%S')
+
+#Function to add NULL
+function add_null () {
+    local a=$1
+    printf '%*s' $a | tr ' ' "\0" >> $FILE
+}
+
+#Function to fetch the size of the dump
+function dump_size () {
+    #Adding 516 bytes as the total dump size is dump tar size
+    #plus the dump header entry in this case
+    #dump_header and dump_entry
+    sizeDump=`expr $dumpSize + $DUMP_HEADER_ENTRY_SIZE`
+    printf -v hex "%x" $sizeDump
+    x=${#hex}
+    if [ $(($x % 2)) -eq 1 ]; then
+        hex=0$hex
+        x=${#hex}
+    fi
+    msize=`expr $x / 2`
+    msize=`expr 8 - $msize`
+    add_null $msize
+    for ((i=0;i<$x;i+=2));
+    do
+        printf \\x${hex:$i:2} >> $FILE
+    done
+}
+
+#Function to set dump id to 8 bytes format
+function get_dump_id () {
+    x=${#dump_id}
+    nulltoadd=`expr 8 - $x`
+    printf '%*s' $nulltoadd | tr ' ' "0" >> $FILE
+    printf $dump_id >> $FILE
+}
+
+#Function to add virtual file directory entry, consists of below entries
+####################FORMAT################
+#Name              Size(bytes)  Value
+#Entry Header      8            FILE
+#Entry Size        2            0x0040
+#Reserved          10           NULL
+#Entry Type        2            0x0001
+#File Name Prefix  2            0x000F
+#Dump File Type    7            BMCDUMP
+#Separator         1            .
+#System Serial No  7            System serial number fetched from system
+#Dump Identifier   8            Dump Identifier value fetched from dump
+#Separator         1            .
+#Time stamp        14           Form should be yyyymmddhhmmss
+#Null Terminator   1            0x00
+function dump_file_entry () {
+    printf "FILE    " >> $FILE
+    add_null 1
+    printf '\x40' >> $FILE #Virtual file directory entry size
+    add_null 11
+    printf '\x01' >> $FILE
+    add_null 1
+    printf '\x0F' >> $FILE
+    printf "BMPDUMP.%s." "$serialNo" >> $FILE
+    get_dump_id
+    printf "." >> $FILE
+    printf $dDay >> $FILE  #UTC time stamp
+    add_null 1
+}
+
+#Function section directory entry, consists of below entries
+####################FORMAT################
+#Name              Size(bytes)  Value
+#Entry Header      8            SECTION
+#Entry Size        2            0x0030
+#Section Priority  2            0x0000
+#Reserved          4            NULL
+#Entry Flags       4            0x00000001
+#Entry Types       2            0x0002
+#Reserved          2            NULL
+#Dump Size         8            Dump size in hex + dump header
+#Optional Section  16           BMCDUMP
+function dump_section_entry () {
+    printf "SECTION " >> $FILE
+    add_null 1
+    printf '\x30' >> $FILE #Section entry size
+    add_null 9
+    printf '\x01' >> $FILE
+    add_null 1
+    printf '\x02' >> $FILE
+    add_null 2
+    dump_size    #Dump size
+    printf "BMCDUMP" >> $FILE
+    add_null 9
+}
+
+#Function to add dump header, consists of below entries
+####################FORMAT################
+#Name              Size(bytes)  Value
+#Dump type         8            BMC DUMP
+#Dump Request time 8            Dump request time stamp (in BCD)
+#Dump Identifier   4            Dump identifer fetched from dump
+#Dump version      2            0x0210
+#Dump header       2            0x200
+#Total dump size   8            Dump size + dump header
+#Panel function    32           System model, feature, type and IPL mode
+#System Name       32           System Name (in ASCII)
+#Serial number     7            System serial number
+#Reserved          1            NULL
+#PLID              4            Comes from errorlog
+#File Header Size  2            0x70
+#Dump SRC Size     2            Dump SRC Size. Currently NULL
+#DUMP SRC          356          DUMP SRC. Currently NULL
+#Dump Req Type     4            Dump requester user interface type.
+#Dump Req ID       32           Dump requester user interface ID
+#Dump Req user ID  8            Dump requester user ID. Currently NULL
+#
+#TODO: Github issue #3707, to populate the unpopulated elements.
+#Note: Unpopulated elements are listed below are set as NULL
+#BCD time stamp
+#PLID
+#SRC size
+#SRC dump
+#Dump requestor
+#Dump requestor user interface ID
+#Dump Requester user ID
+function dump_header () {
+    printf "BMC DUMP" >> $FILE
+    add_null 8 #BCD time stamp
+    add_null 4 #Dump Identifier
+    printf '\x02' >> $FILE #Dump version 0x0210
+    printf '\x10' >> $FILE
+    printf '\x02' >> $FILE #Dump header size 0x0200
+    add_null 1
+    dump_size  #dump size
+    printf $modelNo >> $FILE
+    add_null 24
+    printf "Server-%s-SN-%s" "$modelNo" "$serialNo" >> $FILE
+    add_null 7
+    printf $serialNo >> $FILE
+    add_null 1
+    add_null 4 #PLID
+    printf '\x70' >> $FILE #File header size
+    add_null 2 # SRC size
+    add_null 356 # SRC dump
+    add_null 4 # Dump requester
+    add_null 32 # Dump requester user interface ID
+    add_null 8
+}
+
+#Function to add Dump entry, consists of below entries
+####################FORMAT################
+#Name               Size(bytes)  Value
+#Dump Entry Version 1            0x01
+#BMC Dump Valid     1            0x01
+#No of Dump Entry   2            Number of Dump Entry
+#
+#TODO: Github issue #3707, to populate the unpopulated elements.
+#Note: Unpopulated elements are listed below, currently are set as NULL
+#Number of Dump Entry
+function dump_entry () {
+    printf '\x01' >> $FILE #Dump entry version
+    printf '\x01' >> $FILE #Dump valid
+    add_null 2
+}
+
+#main function
+function gen_header_package () {
+    dump_file_entry
+    dump_section_entry
+    dump_header
+    dump_entry
+}
+
+#Run gen_header_package
+gen_header_package