Fork of the espurna firmware for `mhsw` switches
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

96 lines
4.6 KiB

  1. /*
  2. *
  3. * Created: 29.03.2018
  4. *
  5. * Authors:
  6. *
  7. * Assembled from the code released on Stackoverflow by:
  8. * Dennis (instructable.com/member/nqtronix) | https://stackoverflow.com/questions/23032002/c-c-how-to-get-integer-unix-timestamp-of-build-time-not-string
  9. * and
  10. * Alexis Wilke | https://stackoverflow.com/questions/10538444/do-you-know-of-a-c-macro-to-compute-unix-time-and-date
  11. *
  12. * Assembled by Jean Rabault
  13. *
  14. * UNIX_TIMESTAMP gives the UNIX timestamp (unsigned long integer of seconds since 1st Jan 1970) of compilation from macros using the compiler defined __TIME__ macro.
  15. * This should include Gregorian calendar leap days, in particular the 29ths of February, 100 and 400 years modulo leaps.
  16. *
  17. * Careful: __TIME__ is the local time of the computer, NOT the UTC time in general!
  18. *
  19. */
  20. #ifndef COMPILE_TIME_H_
  21. #define COMPILE_TIME_H_
  22. // Some definitions for calculation
  23. #define SEC_PER_MIN 60UL
  24. #define SEC_PER_HOUR 3600UL
  25. #define SEC_PER_DAY 86400UL
  26. #define SEC_PER_YEAR (SEC_PER_DAY*365)
  27. // extracts 1..4 characters from a string and interprets it as a decimal value
  28. #define CONV_STR2DEC_1(str, i) (str[i]>'0'?str[i]-'0':0)
  29. #define CONV_STR2DEC_2(str, i) (CONV_STR2DEC_1(str, i)*10 + str[i+1]-'0')
  30. #define CONV_STR2DEC_3(str, i) (CONV_STR2DEC_2(str, i)*10 + str[i+2]-'0')
  31. #define CONV_STR2DEC_4(str, i) (CONV_STR2DEC_3(str, i)*10 + str[i+3]-'0')
  32. // Custom "glue logic" to convert the month name to a usable number
  33. #define GET_MONTH(str, i) (str[i]=='J' && str[i+1]=='a' && str[i+2]=='n' ? 1 : \
  34. str[i]=='F' && str[i+1]=='e' && str[i+2]=='b' ? 2 : \
  35. str[i]=='M' && str[i+1]=='a' && str[i+2]=='r' ? 3 : \
  36. str[i]=='A' && str[i+1]=='p' && str[i+2]=='r' ? 4 : \
  37. str[i]=='M' && str[i+1]=='a' && str[i+2]=='y' ? 5 : \
  38. str[i]=='J' && str[i+1]=='u' && str[i+2]=='n' ? 6 : \
  39. str[i]=='J' && str[i+1]=='u' && str[i+2]=='l' ? 7 : \
  40. str[i]=='A' && str[i+1]=='u' && str[i+2]=='g' ? 8 : \
  41. str[i]=='S' && str[i+1]=='e' && str[i+2]=='p' ? 9 : \
  42. str[i]=='O' && str[i+1]=='c' && str[i+2]=='t' ? 10 : \
  43. str[i]=='N' && str[i+1]=='o' && str[i+2]=='v' ? 11 : \
  44. str[i]=='D' && str[i+1]=='e' && str[i+2]=='c' ? 12 : 0)
  45. // extract the information from the time string given by __TIME__ and __DATE__
  46. #define __TIME_SECOND__ (CONV_STR2DEC_2(__TIME__, 6))
  47. #define __TIME_MINUTE__ (CONV_STR2DEC_2(__TIME__, 3))
  48. #define __TIME_HOUR__ (CONV_STR2DEC_2(__TIME__, 0))
  49. #define __TIME_DAY__ (CONV_STR2DEC_2(__DATE__, 4))
  50. #define __TIME_MONTH__ (GET_MONTH(__DATE__, 0))
  51. #define __TIME_YEAR__ (CONV_STR2DEC_4(__DATE__, 7))
  52. // Days in February
  53. #define _UNIX_TIMESTAMP_FDAY(year) \
  54. (((year) % 400) == 0UL ? 29UL : \
  55. (((year) % 100) == 0UL ? 28UL : \
  56. (((year) % 4) == 0UL ? 29UL : \
  57. 28UL)))
  58. // Days in the year
  59. #define _UNIX_TIMESTAMP_YDAY(year, month, day) \
  60. ( \
  61. /* January */ day \
  62. /* February */ + (month >= 2 ? 31UL : 0UL) \
  63. /* March */ + (month >= 3 ? _UNIX_TIMESTAMP_FDAY(year) : 0UL) \
  64. /* April */ + (month >= 4 ? 31UL : 0UL) \
  65. /* May */ + (month >= 5 ? 30UL : 0UL) \
  66. /* June */ + (month >= 6 ? 31UL : 0UL) \
  67. /* July */ + (month >= 7 ? 30UL : 0UL) \
  68. /* August */ + (month >= 8 ? 31UL : 0UL) \
  69. /* September */+ (month >= 9 ? 31UL : 0UL) \
  70. /* October */ + (month >= 10 ? 30UL : 0UL) \
  71. /* November */ + (month >= 11 ? 31UL : 0UL) \
  72. /* December */ + (month >= 12 ? 30UL : 0UL) \
  73. )
  74. // get the UNIX timestamp from a digits representation
  75. #define _UNIX_TIMESTAMP(year, month, day, hour, minute, second) \
  76. ( /* time */ second \
  77. + minute * SEC_PER_MIN \
  78. + hour * SEC_PER_HOUR \
  79. + /* year day (month + day) */ (_UNIX_TIMESTAMP_YDAY(year, month, day) - 1) * SEC_PER_DAY \
  80. + /* year */ (year - 1970UL) * SEC_PER_YEAR \
  81. + ((year - 1969UL) / 4UL) * SEC_PER_DAY \
  82. - ((year - 1901UL) / 100UL) * SEC_PER_DAY \
  83. + ((year - 1601UL) / 400UL) * SEC_PER_DAY \
  84. )
  85. // the UNIX timestamp
  86. #define __UNIX_TIMESTAMP__ (_UNIX_TIMESTAMP(__TIME_YEAR__, __TIME_MONTH__, __TIME_DAY__, __TIME_HOUR__, __TIME_MINUTE__, __TIME_SECOND__))
  87. #endif