点击上方“中兴开发者社区”,关注我们
每天读一篇一线开发者原创好文
▍作者简介
作者韩相国是中兴通讯敏捷技术教练,产品平台领域BA,目前主要研究各类开源软件,结合电信类产品特点,适配并将开源软件应用到产品中。本文讨论了Linux系统中的时区和夏令时的概念,深入分析时区原理,并根据学习内容自行定义时区夏令时配置。
使用Linux的TX经常会感到困惑,机器上安装了Windows和Linux双系统,为何到了Linux系统后时间总是不对,跟Windows相差几个小时?
其实这个就是Linux时区配置不正确导致的,下面详细介绍一下Linux系统中时间、时区的原理和相关配置,开始之前我们先介绍几个概念:
GMT/UTC Time:这个就是所谓的格林威治所在地的本地时间,世界上所有国家的时间都是以此时间为基准;
Local Time:所在位置的当地时间,一般是GMT时间的基础上增加或者减去0-12小时;
RTC Time:指的是机器硬件BIOS中保存的时间,一般此时间保存的是GMT时间;
DST:是“Daylight Saving Time”的缩写,也就是平时说的夏令时;
▍系统时间配置
通过date命令可以修改系统的时间,最简单的data命令格式如下:
将系统时间修改为2017.3.12 01.59.50:
通过timedatectl可以看到系统时间已经修改了,但是硬件RTC时间并没有变更,如果发生重启,系统时间又会恢复到原来的值,所以这里需要将系统时钟同步到RTC硬件中:
验证,可以看到系统时钟和UTC时钟相同了:
▍时区相关
查看当前时区
有两种方式可以查看当前时区,date和timedatectl,使用后者能够显示更详细的信息。
1、通过date查看,在行末打印有-0400,表示相对UTC时间减去4小时:
2、通过timedatectl查看,信息比较详细:
▍时区文件
时区相关的信息全部保存在/usr/share/zoneinfo目录下,这里按照地域进行区分,文件中保存了该时区下的一些参数,例如夏令时时间,使用zdump -v命令可以看到该时区下的夏令时参数:
下面以美国纽约的时区为例,此命令会显示出该时区夏令时切换时间,一直到2499年:
从上面的打印我们可以看到UTC时间和美国EST时间的对应关系,2499年发生夏令时切换的时间信息。
修改时区
linux系统使用/etc/localtime配置文件作为本机的时区配置,将时区文件链接到/etc/localtime即可更改时区:
验证夏令时切换
我们看下NewYork在2017年的夏令时切换时间:
将系统时间修改为 2017.3.12 01.59.50:
然后隔10秒后重新查看时间,我们可以看到系统的Local时间发生了跳跃,从2点直接切换到了3点,时区名从EST切换到EDT,切换过程中UTC的时间保持不变。
▍自定义时区
Linux的时区文件由国际标准组织IANA维护,其数据保存在/usr/share/zoneinfo目录下,文件格式为tzdata,此文件可以从https://www.iana.org/time-zones下载,下载时选择Data文件。
如果我需要的时区不Linux系统中怎么办呢?您可以自定义。
时区配置文件格式
时区配置文件格式为tzdata,是二进制文件,tzdata的源文件文本文件,通过zic命令可以将源文件编译成二进制文件。
tzdata源文件由Rule和Zone两部分组成:
1、Rule的格式:
2、Zone的格式:
关于tzdata文件格式,可以参考:https://www.iana.org/time-zones/repository/tz-how-to.html,tzdata文件使用zic命令编译,zic命令参考。
创建时区文件
接下来创建一个自定义的tzdata文件,要求:
从2000年开始执行夏令时时间;
夏令时开始时间为3月最后一个周日,结束时间为8月最后一个周日,夏令时时间推迟1小时;
时区名字:夏令时为UDEFST,普通时间为UDEFDT;
时区文件名为han;
1、创建tzdata源文件hxg(注意文件末尾必须有空行):
2、使用zic命令编译源文件,生成tzdata二进制文件,生成的时区文件为/usr/share/zoneinfo/han:
3、设置当前系统使用此时区文件:
当然还有另外一种更粗暴的方式,直接拷贝文件覆盖localtime文件就可以了:
4、查看应用结果,时区显示正常: