release 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295
  1. #!/usr/bin/env sh
  2. # SPDX-License-Identifier: MIT
  3. # SPDX-FileCopyrightText: 2020-2023 Leah Rowe <leah@libreboot.org>
  4. set -u -e
  5. . "include/err.sh"
  6. . "include/option.sh"
  7. eval "$(setvars "" vdir relname src_dirname srcdir _xm target romdir \
  8. microcode_required mode)"
  9. main()
  10. {
  11. vdir="release"
  12. while getopts d:m: option; do
  13. [ -z "${OPTARG}" ] && err "Empty argument not allowed"
  14. case "${option}" in
  15. d) vdir="${OPTARG}" ;;
  16. m) mode="${OPTARG}" ;;
  17. *) err "Invalid option" ;;
  18. esac
  19. done
  20. vdir="${vdir}/${version}"
  21. relname="${projectname}-${version}"
  22. src_dirname="${relname}_src"
  23. srcdir="${vdir}/${src_dirname}"
  24. [ -e "${vdir}" ] && err "already exists: \"${vdir}\""
  25. mkvdir
  26. build_release
  27. printf "DONE! Check release files under %s\n" "${vdir}"
  28. }
  29. mkvdir()
  30. {
  31. mkdir -p "${vdir}" || err "mkvdir: !mkdir -p \"${vdir}\""
  32. git clone . "${srcdir}" || err "mkdir: !gitclone \"${srcdir}\""
  33. insert_version_files "${srcdir}" || err "mkvdir ${srcdir}: versionfile"
  34. }
  35. build_release()
  36. {
  37. _xm="build_release ${vdir}"
  38. (
  39. cd "${srcdir}" || err "${_xm}: !cd \"${srcdir}\""
  40. fetch_trees
  41. x_ mv src/docs docs
  42. ) || err "can't copy docs"
  43. (
  44. cd "${srcdir%/*}" || err "${_xm}: mktarball \"${srcdir}\""
  45. mktarball "${srcdir##*/}" "${srcdir##*/}.tar.xz" || err "${_xm}: mksrc"
  46. ) || err "can't create pre-crossgcc src tarball"
  47. [ "${mode}" = "src" ] && return 0 # for src mode, xgcc tarballs are
  48. # not included in the src archive
  49. # now build roms, then copy crossgcc to src and re-compress
  50. # while compressing rom images too.
  51. (
  52. cd "${srcdir}" || err "${_xm}: 2 !cd \"${srcdir}\""
  53. mkrom_images
  54. ) || err "can't build rom images"
  55. for _cbd in "${srcdir}/src/coreboot/"*; do
  56. [ -d "${_cbd}/util/crossgcc/tarballs" ] || continue
  57. _xgccdir="${vdir}/crossgcc/${_cbd##*/}"
  58. mkdir -p "${_xgccdir}" || \
  59. err "build_release: !mkdir -p ${_xgccdir}"
  60. cp -R "${_cbd}/util/crossgcc/tarballs/"* "${_xgccdir}" || \
  61. err "build_gcc: !copy xgcc ${_cbd}"
  62. done
  63. rm -Rf "${srcdir}" || err "build_release: !rm -Rf ${srcdir}"
  64. (
  65. cd "${srcdir%/*}" || err "${_xm} 2: mktarball \"${srcdir}\""
  66. tar -xf "${srcdir##*/}.tar.xz" || err "!extract ${srcdir##*/}.tar.xz"
  67. rm -f "${srcdir##*/}.tar.xz" || err "!rm -f ${srcdir##*/}.tar.xz"
  68. ) || err "can't extract pre-crossgcc src tarball"
  69. for _xgcc in "${vdir}/crossgcc/"*; do
  70. [ -d "${_xgcc}" ] || continue
  71. mkdir -p "${srcdir}/src/coreboot/${_xgcc##*/}/util/crossgcc/tarballs" || \
  72. err "!mkdir src/coreboot/${_xgcc##*/}/util/crossgcc/tarballs"
  73. mv "${_xgcc}/"* \
  74. "${srcdir}/src/coreboot/${_xgcc##*/}/util/crossgcc/tarballs/" \
  75. || err "!move xgcc tarballs to ${srcdir}/xgcc/${_xgcc##*/}"
  76. done
  77. rm -Rf "${vdir}/crossgcc" || err "!rm -Rf \"${vdir}/crossgcc\""
  78. (
  79. cd "${srcdir%/*}" || err "${_xm}: mktarball \"${srcdir}\""
  80. mktarball "${srcdir##*/}" "${srcdir##*/}.tar.xz" || err "${_xm}: mksrc"
  81. ) || err "can't create src tarball with crossgcc"
  82. # now test the vendor insert script, using the release archive:
  83. (
  84. cd "${srcdir}" || err "!cd ${srcdir}"
  85. mkfakeroms
  86. for vrom in ../roms/*.tar.xz; do
  87. [ -f "${vrom}" ] || continue
  88. case "${vrom}" in
  89. *serprog*) continue ;;
  90. esac
  91. ./vendor inject "${vrom}" || \
  92. err "TESTFAIL: inject: ${vrom##*/}"
  93. continue
  94. done
  95. ) || err "vendorfile inject test failure"
  96. rm -Rf "${srcdir}" || err "!rm -Rf ${srcdir}"
  97. }
  98. fetch_trees()
  99. {
  100. for x in config/git/*; do
  101. [ ! -f "${x}" ] || ./update trees -f "${x#config/git/}" || \
  102. err "${_xm}: fetch ${x#config/git/}"
  103. done
  104. for x in config/*/build.list; do
  105. [ -f "${x}" ] || continue
  106. xp="${x#*/}"; xp="${xp%/*}"
  107. [ -L "${xp}" ] || rm -Rf "src/${xp}/${xp}" || \
  108. err "!rm -Rf \"src/${xp}/${xp}\""
  109. done
  110. find . -name ".git" -exec rm -Rf {} + || err "${_xm}: rm .git"
  111. find . -name ".gitmodules" -exec rm -Rf {} + || err "${_xm}: rm .gitmod"
  112. x_ rm -Rf tmp .git
  113. }
  114. mkrom_images()
  115. {
  116. mkfakeroms
  117. ./build roms all || err "${_xm}: roms-all"
  118. ./build serprog rp2040 || err "${_xm}: rp2040"
  119. ./build serprog stm32 || err "${_xm}: stm32"
  120. for rombuild in bin/*; do
  121. [ -d "${rombuild}" ] || continue
  122. handle_rom_archive "${rombuild}"
  123. done
  124. mv "release/${version}/roms/" ../roms || err "${_xm}: copy roms/"
  125. }
  126. mkfakeroms()
  127. {
  128. # fake me.bin to make x201 roms build
  129. mkdir -p "vendorfiles/x201/" || \
  130. err "mkvdir: !mkdir -p \"vendorfiles/x201/\""
  131. dd if=/dev/zero of="vendorfiles/x201/me.bin" \
  132. bs=68k count=1 || err "mkvdir: can't make fake x201 me.bin"
  133. }
  134. handle_rom_archive()
  135. {
  136. builddir="${1}"
  137. romdir="tmp/romdir"
  138. rm -Rf "${romdir}" || err "!rm romdir, handle_rom_archive"
  139. target="${builddir##*/}"
  140. if [ ! -f "config/coreboot/${target}/target.cfg" ]; then
  141. # No config, just make a tarball
  142. tarball="release/${version}/roms/${relname}_${target}.tar.xz"
  143. insert_copying_files "${builddir}" || \
  144. err "!insert copy, handle, ${builddir}"
  145. mktarball "${builddir}" "${tarball}"
  146. return 0
  147. fi
  148. romdir="${romdir}/bin/${target}"
  149. mkdir -p "${romdir}" || err "!mkdir -p romdir, handle_rom_archive"
  150. cp "${builddir}/"* "${romdir}" || err "!cp romdir, handle_rom_archive"
  151. nukerom
  152. printf "Generating release/%s/roms/%s-%s_%s.tar.xz\n" \
  153. "${version}" "${projectname}" "${version}" "${target##*/}"
  154. insert_version_files "${romdir}" || \
  155. err "mkrom_tarball ${romdir}: versionfile"
  156. insert_copying_files "${romdir}" || err "!insert copy, handle 2, ${romdir}"
  157. mkrom_tarball
  158. }
  159. nukerom()
  160. {
  161. microcode_required="y"
  162. . "config/coreboot/${target}/target.cfg"
  163. if [ "${microcode_required}" != "y" ] && \
  164. [ "${microcode_required}" != "n" ]; then microcode_required="y"; fi
  165. if [ "${microcode_required}" = "n" ]; then
  166. for romfile in "${romdir}"/*.rom; do
  167. [ -f "${romfile}" ] || continue
  168. strip_ucode "${romfile}"
  169. done
  170. for romfile in "${romdir}"/*.tmprom; do
  171. [ -f "${romfile}" ] || continue
  172. mv "${romfile}" "${romfile%.tmprom}.rom" || \
  173. err "!mv romfile, nukerom"
  174. done
  175. fi
  176. # Hash the images before removing vendor files
  177. # which "./vendor inject" uses for verification
  178. rm -f "${romdir}/vendorhashes" || err "!rm ${romdir}/vendorhashes"
  179. touch "${romdir}/vendorhashes" || err "!touch ${romdir}/vendorhashes"
  180. (
  181. cd "${romdir}" || err "!cd romdir ${romdir}, nukerom"
  182. sha512sum ./*.rom >> vendorhashes || err "!create vendorhashes, nukerom"
  183. ) || err "can't create vendor hashes"
  184. for romfile in "${romdir}"/*.rom; do
  185. [ -f "${romfile}" ] || continue
  186. ./vendor inject -r "${romfile}" -b "${target}" -n nuke || \
  187. err "!vendor inject (nuke) ${romfile}, nukerom"
  188. done
  189. }
  190. strip_ucode()
  191. {
  192. romfile=${1}
  193. _newrom_b="${romfile%.rom}_nomicrocode.tmprom"
  194. cp "${romfile}" "${_newrom_b}" || err "!cp romfile ${romfile}, strip_u"
  195. microcode_present="y"
  196. "${cbfstool}" "${_newrom_b}" remove -n \
  197. cpu_microcode_blob.bin 2>/dev/null || microcode_present="n"
  198. [ "${microcode_present}" = "n" ] || return 0
  199. printf "REMARK: '%s' already lacks microcode\n" "${romfile}" 1>&2
  200. printf "Renaming default ROM file instead.\n" 1>&2
  201. mv "${romfile}" "${_newrom_b}" || err "!mv romfile ${romfile}, strip_u"
  202. }
  203. insert_copying_files()
  204. {
  205. rm -Rf "${1}/licenses" || return 1
  206. mkdir -p "${1}/licenses" || return 1
  207. l="${1}/licenses"
  208. # copy licenses to rom image archive, for completion
  209. cp "src/grub/COPYING" "${l}/COPYING.grub" || return 1
  210. cp "src/coreboot/default/COPYING" "${l}/COPYING.coreboot" || return 1
  211. cp -R "src/coreboot/default/LICENSES" "${l}/LICENSES.coreboot" || return 1
  212. cp "src/seabios/default/COPYING" "${l}/COPYING.coreboot" || return 1
  213. cp "src/seabios/default/COPYING.LESSER" "${l}/COPYING.LESSER.seabios" || return 1
  214. cp -R "src/u-boot/default/Licenses" "${l}/COPYING.u-boot" || return 1
  215. printf "Multiple licenses. Check corresponding %s source archive\n" \
  216. "${projectname}" > "${1}/COPYING" || return 1
  217. }
  218. mkrom_tarball()
  219. {
  220. archivename="${relname}_${target##*/}"
  221. f="release/${version}/roms/${archivename}"
  222. mkdir -p "${f%/*}" || err "mkrom_tarball: !mkdir -p ${f%/*}"
  223. (
  224. cd "${romdir%"/bin/${target}"}" || err "!cd ${romdir%"/bin/${target}"}"
  225. mktarball "bin/${target}" "${archivename}.tar.xz"
  226. ) || err "can't create rom tarball"
  227. mv "${romdir%"/bin/${target}"}/${archivename}.tar.xz"* "${f%/*}" || \
  228. err "!mktarball, rom, ${f%/*}/${romdir%"/bin/${target}"}/${archivename}.tar.xz"
  229. printf "Created ROM archive: %s" "${f%/*}/${archivename}.tar.xz"
  230. }
  231. insert_version_files()
  232. {
  233. printf "%s\n" "${version}" > "${1}/version" || return 1
  234. printf "%s\n" "${versiondate}" > "${1}/versiondate" || return 1
  235. printf "%s\n" "${projectname}" > "${1}/projectname" || return 1
  236. }
  237. mktarball()
  238. {
  239. # preserve timestamps for reproducible tarballs
  240. tar_implementation=$(tar --version | head -n1) || :
  241. [ "${2%/*}" = "${2}" ] || mkdir -p "${2%/*}" || err "mk, !mkdir -p \"${2%/*}\""
  242. if [ "${tar_implementation% *}" = "tar (GNU tar)" ]; then
  243. tar --sort=name --owner=root:0 --group=root:0 \
  244. --mtime="UTC 2023-11-06" -c "${1}" | xz -T0 -9e > "${2}" || \
  245. err "mktarball 1, ${1}"
  246. else
  247. # TODO: reproducible tarballs on non-GNU systems
  248. tar -c "${1}" | xz -T0 -9e > "${2}" || err "mktarball 2, ${1}"
  249. fi
  250. (
  251. [ "${2%/*}" != "${2}" ] && x_ cd "${2%/*}"
  252. sha512sum "${2##*/}" > "${2##*/}.sha512" || \
  253. err "!sha512sum \"${2##*/}\" > \"${2##*/}.sha512\""
  254. ) || err "failed to create tarball checksum"
  255. }
  256. main $@