OpenWrt uboot 编译时间戳问题

OpenWrt uboot 编译时间戳问题

背景

在uboot 启动过程中会有如下打印:

U-Boot SPL 2017.11 (Aug 16 2018 - 07:51:15)
DRAM: 128 MiB
Trying to boot from MMC1

U-Boot 2017.11 (Aug 16 2018 - 07:51:15 +0000) Allwinner Technology

通常我们需要通过编译时间来区分uboot 版本。在使用OpenWrt 编译时uboot 时发现上面的时间戳并不会变。造成版本不易区分问题。

要解决这问题需要清楚:

  • 编译时间戳是如何生成的?

uboot 编译时间戳是如何生成的?

在uboot 的Makefile 中有如下定义

# The SOURCE_DATE_EPOCH mechanism requires a date that behaves like GNU date.
# The BSD date on the other hand behaves different and would produce errors
# with the misused '-d' switch.  Respect that and search a working date with
# well known pre- and suffixes for the GNU variant of date.
define filechk_timestamp.h
        (if test -n "$${SOURCE_DATE_EPOCH}"; then \
                SOURCE_DATE="@$${SOURCE_DATE_EPOCH}"; \
                DATE=""; \
                for date in gdate date.gnu date; do \
                        $${date} -u -d "$${SOURCE_DATE}" >/dev/null 2>&1 && DATE="$${date}"; \
                done; \
                if test -n "$${DATE}"; then \
                        LC_ALL=C $${DATE} -u -d "$${SOURCE_DATE}" +'#define U_BOOT_DATE "%b %d %C%y"'; \
                        LC_ALL=C $${DATE} -u -d "$${SOURCE_DATE}" +'#define U_BOOT_TIME "%T"'; \
                        LC_ALL=C $${DATE} -u -d "$${SOURCE_DATE}" +'#define U_BOOT_TZ "%z"'; \
                        LC_ALL=C $${DATE} -u -d "$${SOURCE_DATE}" +'#define U_BOOT_DMI_DATE "%m/%d/%Y"'; \
                        LC_ALL=C $${DATE} -u -d "$${SOURCE_DATE}" +'#define U_BOOT_BUILD_DATE 0x%Y%m%d'; \
                else \
                        return 42; \
                fi; \
        else \
                LC_ALL=C date +'#define U_BOOT_DATE "%b %d %C%y"'; \
                LC_ALL=C date +'#define U_BOOT_TIME "%T"'; \
                LC_ALL=C date +'#define U_BOOT_TZ "%z"'; \
                LC_ALL=C date +'#define U_BOOT_DMI_DATE "%m/%d/%Y"'; \
                LC_ALL=C date +'#define U_BOOT_BUILD_DATE 0x%Y%m%d'; \
        fi)
endef

这上面首先判断在环境变量中是否定义了 SOURCE_DATE_EPOCH ,有则使用 SOURCE_DATE_EPOCH 生成时间戳,没有则使用当前时间。

在OpenWrt 的编译环境中,是会定义 SOURCE_DATE_EPOCH 的,位于openwrt/include/toplevel.mk

ifeq ($(SDK),1)
  include $(TOPDIR)/include/version.mk
else
  REVISION:=$(shell $(TOPDIR)/scripts/getver.sh)
  SOURCE_DATE_EPOCH:=$(shell $(TOPDIR)/scripts/get_source_date_epoch.sh)
endif

其使用 $(TOPDIR)/scripts/get_source_date_epoch.sh 来获取时间戳,scripts/get_source_date_epoch.sh 内容如下:

#!/usr/bin/env bash
export LANG=C
export LC_ALL=C
[ -n "$TOPDIR" ] && cd $TOPDIR

try_version() {
        [ -f version.date ] || return 1
        SOURCE_DATE_EPOCH="$(cat version.date)"
        [ -n "$SOURCE_DATE_EPOCH" ]
}

try_git() {
        [ -e .git ] || return 1
        SOURCE_DATE_EPOCH="$(git log -1 --format=format:%ct)"
        [ -n "$SOURCE_DATE_EPOCH" ]
}

try_hg() {
        [ -d .hg ] || return 1
        SOURCE_DATE_EPOCH="$(hg log --template '{date}' -l 1 | cut -d. -f1)"
        [ -n "$SOURCE_DATE_EPOCH" ]
}

try_mtime() {
        perl -e 'print((stat $ARGV[0])[9])' "$0"
        [ -n "$SOURCE_DATE_EPOCH" ]
}

try_version || try_git || try_hg || try_mtime || SOURCE_DATE_EPOCH=""
echo "$SOURCE_DATE_EPOCH"

其首先从 version.date 文件中读取时间戳,失败的话尝试使用git ,hg ,mtime 时间戳。

而我当前环境是存在 version.date 文件的

openwrt$ cat version.date
1534405875

这就难怪每次编译uboot 时间戳都是一样的了( Aug 16 2018 - 07:51:15)。

解决:

#!/usr/bin/env bash
export LANG=C
export LC_ALL=C
[ -n "$TOPDIR" ] && cd $TOPDIR


try_date_now(){
        SOURCE_DATE_EPOCH="$(date +%s)"
}
...

try_date_now ||try_version || try_git || try_hg || try_mtime || SOURCE_DATE_EPOCH=""
echo "$SOURCE_DATE_EPOCH"

猜你喜欢

转载自blog.csdn.net/agave7/article/details/108750238