B4R Question ESP8266 Time from NIST server and summer/winter time

BaGRoS

Active Member
Licensed User
Longtime User
Hey!
I use Erel example from
https://www.b4x.com/android/forum/threads/esp8266-requesting-time-from-a-server.68636/
with small modification by pappicio https://www.b4x.com/android/forum/threads/esp8266-requesting-time-from-a-server.68636/#post-511310
but big question is how changing hours for summer/winter time.

UK summer 26/03 01:00
winter 29/10 02:00
but only in this year :(

I need help with verification, I write some code (with Erel example):
B4X:
Sub Process_Globals
    Private tmr As Timer
    Private socket As WiFiSocket
    Private lastMillis As ULong   
    Private astream As AsyncStreams
    Private date(8) As Byte
    Private bc As ByteConverter
    Private seconds As ULong
    Private firstTime As Boolean = True
   
    Private summer As Boolean = False
   
End Sub

Public Sub Start
    tmr.Initialize("tmr_Tick", 60 * 1000) 'check with server every minute
    tmr.Enabled = True
    tmr_Tick
End Sub

Private Sub tmr_Tick
    Connect(0)
End Sub

Private Sub Connect(u As Byte)
    Log("Connecting to NIST server...")
    If socket.ConnectHost("time.nist.gov", 13) Then
        astream.Initialize(socket.Stream, "astream_NewData", "astream_Error")
    Else
        Log("Failed to connect to NIST server")
        CallSubPlus("Connect", 1000, 0)
    End If
End Sub


Private Sub AStream_NewData (Buffer() As Byte)
    Log(Buffer)
    Dim i As Byte = 0
    For Each s() As Byte In bc.Split(Buffer, " ")
        Select i
            Case 1
                bc.ArrayCopy(s, date)
            Case 2
                Dim multi As UInt = 3600
                seconds = 0
                For Each s2() As Byte In bc.Split(s, ":")
                    seconds = seconds + multi * bc.StringFromBytes(s2) 'need to convert the bytes into string before they can be parsed as a number
                    multi = multi / 60
                Next
        End Select
        i = i + 1
        lastMillis = Millis
    Next
    socket.Close
    If firstTime Then
        Main.TimeIsAvailable
        firstTime = False
    End If
   
    'check summer...
    CheckSummerTime
   
End Sub

Public Sub GetDate As Byte()
    Return date
End Sub

Private Sub GetUpdatedTotalSeconds As ULong
    Return seconds + (Millis - lastMillis) / 1000
End Sub

'Public Sub GetHours As UInt
'    Return Floor(GetUpdatedTotalSeconds/ 3600)
'End Sub

Public Sub GetHours As UInt
    Dim u As UInt = Floor(GetUpdatedTotalSeconds / 3600)
   
    If summer Then
           
        Log("Summer time")
        u = u + 1  'for UK summer
        If u > 23 Then
            u = u - 24
        End If
       
    Else
       
        Log("Winter time")
   
    End If
   
   
    Return    u
End Sub

Public Sub GetMinutes As UInt
    Dim minutes As Int = Floor(GetUpdatedTotalSeconds / 60)
    Return minutes Mod 60
End Sub

Public Sub GetSeconds As UInt
    Return GetUpdatedTotalSeconds Mod 60
End Sub

Private Sub AStream_Error
    Log("Disconnected")
End Sub

Private Sub GetMonth As UInt
   
    Return bc.StringFromBytes(bc.SubString2(date,4,6))
       
End Sub

Private Sub GetDay As UInt

    Return bc.StringFromBytes(bc.SubString2(date,6,8))
       
End Sub

Private Sub GetYear As UInt
   
    Return bc.StringFromBytes(bc.SubString2(date,0,3))
   
End Sub

Private Sub CheckSummerTime
    'All day for London
    'https://www.timeanddate.com/time/change/uk/london
   
    Dim u As UInt = Floor(GetUpdatedTotalSeconds / 3600)
    summer = False
   
    'Summer time or Winter is coming....
    Dim year As UInt = GetYear
    'days when summer is begining from 2017-2029 for London!
    Dim data_sum(12) As Byte = Array As Byte(26,25,31,29,28,27,26,31,30,29,28,26,25)
    Dim summer_day As Byte = data_sum(year-17)
    'days when summer is ending from 2017-2029 for London!
    Dim data_wint(12) As Byte = Array As Byte(29,28,27,25,31,30,29,27,26,25,31,29,28)
    Dim winter_day As Byte = data_wint(year-17)
    Dim month As UInt = GetMonth
    Dim day As UInt = GetDay
       
    Log("Y:", year, " - M:", month, " - D:", day, " - h:", u)
    'month 04 - month 09 100% summer
    If (month > 3 ) And (month < 10) Then
        summer = True
    End If
    'month 03 and day > summer_day 100% summer
    If month = 3 And day > summer_day Then
        summer = True
        'month 03, day summer_day and 1 hour then start summer
    Else If month = 3 And day = summer_day And u > 0 Then
        summer = True
    End If
   
    'month 10 and day < winter_day is still summer
    If month = 10 And day < winter_day Then
        summer=True
        'month 10, day winter_day and 2 then Winter is coming..... :(
    else if month = 10 And day = winter_day And u < 2 Then
        summer=True
    End If
   
End Sub

most important is Private Sub CheckSummerTime, optimizations?
 

BaGRoS

Active Member
Licensed User
Longtime User
First BUG
B4X:
If summer Then
           
        Log("Summer time")
        u = u + 1  'for UK summer
        If u > 23 Then
            u = u - 24
           
        End If
       
    Else
       
        Log("Winter time")
   
    End If

If u>23 then is next day...
UTC 23:20 17-09-04
but local
00:20 17-09-05...
This is big problem, because if next day then 31+1 = next month...
 
Upvote 0

BaGRoS

Active Member
Licensed User
Longtime User
Yes, it will not change anything.
For example:
UTC 17-09-04 23:10 in the UK should be 17-09-05 00:10
So I have to change the hour and the day!
UTC 17-07-31 23:10 in the UK should be 17-08-01 00:10
The hour, day and month change.
That is more complicated, I have to check the length of months.
 
Upvote 0
Top