Page 1 of 2
Posted: Sun Dec 29, 2002 7:42 am
by BackupUser
Restored from previous forum. Originally posted by boop64.
Here is a short piece of code I wrote to get the current system up time I hope it helps someone out there.
;-------------------------------------
;A simple procedure that will return the current system uptime
Procedure.s uptime()
uptime.f = GetTickCount_() ;gets the system uptime in miliseconds
;determine hours
upth.f = uptime/3600000
;determine minutes
rmnd.f = upth - Round(upth,0)
uptm.f = rmnd*60
;determine seconds
rmnd = uptm - Round(uptm,0)
upts.f = rmnd*60
;determine miliseconds
rmnd = upts - Round(upts,0)
uptms.f = rmnd*1000
;Format the string to H:M:S.MS
sysuptime.s = Str(upth) + ":" + Str(uptm) + ":" + Str(upts) + "." + Str(uptms)
ProcedureReturn sysuptime
EndProcedure
MessageRequester("System Up Time", uptime(),0)
;------------------------------------
It's simple, it's short and best of all.... it works!

If you like this sample or want to complain about it leave a post.
Boop64
Posted: Sun Dec 29, 2002 10:13 am
by BackupUser
Restored from previous forum. Originally posted by PB.
> uptime.f = GetTickCount_() ;gets the system uptime in miliseconds
Don't forget that GetTickCount resets after 49 days, so if your PC's
uptime normally goes longer than that, then problems will arise.
Posted: Sun Dec 29, 2002 8:39 pm
by BackupUser
Restored from previous forum. Originally posted by boop64.
Originally posted by PB
Don't forget that GetTickCount resets after 49 days, so if your PC's
uptime normally goes longer than that, then problems will arise.
Thanks, I did not know that. I just came accross it while I was teaching my self to use the windows api with purebasic. Just for reference, how would get the system uptime after that 49 days? Is there another function to do it or would you have to make your program keep track of it by logging the uptime?
Boop64
Posted: Mon Dec 30, 2002 3:19 pm
by BackupUser
Restored from previous forum. Originally posted by ebs.
Boop64,
It resets after approximately 49 days because the number of milliseconds is held in a 32-bit number:
2**32 = 4,294,967,296
and 49 days of milliseconds is:
49 * 24 * 60 * 60 * 1,000 = 4,233,600,000
It sounds like a good idea to have your program record each 49 days of uptime.
Regards,
Eric
Originally posted by boop64
Originally posted by PB
Don't forget that GetTickCount resets after 49 days, so if your PC's
uptime normally goes longer than that, then problems will arise.
Thanks, I did not know that. I just came accross it while I was teaching my self to use the windows api with purebasic. Just for reference, how would get the system uptime after that 49 days? Is there another function to do it or would you have to make your program keep track of it by logging the uptime?
Boop64
Posted: Mon Dec 30, 2002 3:55 pm
by BackupUser
Restored from previous forum. Originally posted by freak.
There's another thing you need to be aware of:
PureBasics Variables are SIGNED! This means, after 24.5 Days, GetTickCount_() returns negative Values.
Timo
Posted: Wed Jan 01, 2003 7:19 am
by BackupUser
Restored from previous forum. Originally posted by boop64.
Originally posted by freak
There's another thing you need to be aware of:
PureBasics Variables are SIGNED! This means, after 24.5 Days, GetTickCount_() returns negative Values.
Timo
How would you fix this problems?.... Couldn't you just take the absolute value of the tick count, something similar to this?
uptime.f = GetTickCount()
uptime = abs(uptime)
Posted: Wed Jan 01, 2003 7:45 am
by BackupUser
Restored from previous forum. Originally posted by pusztry.
Is there a good way to get it past the ~49 day limit? Could you use a log file some how? I am struggleing with this. I could realy use some help.
- Ryan
WinXP, PIII 800 MHz, 512MB RAM, SB Live 5.1, NVidia TNT 2 Ultra
Posted: Wed Jan 01, 2003 5:48 pm
by BackupUser
Restored from previous forum. Originally posted by PB.
> Is there a good way to get it past the ~49 day limit?
If you just want to record the uptime with a per-second accuracy (not
a per-millisecond accuracy), then just use the tip I gave here:
viewtopic.php?t=2777
Posted: Thu Jan 02, 2003 4:02 am
by BackupUser
Restored from previous forum. Originally posted by boop64.
Originally posted by pusztry
Is there a good way to get it past the ~49 day limit?
One way you could log the uptime is to write the uptime to an ini file or you could use the registry like I am doing. And once you have written the value of the current uptime make a fuction that compares the current uptime value to the stored uptime value... something similar to this:
;Use an if statement similar to this once you have loaded
;the StoredUpTime from the file or registry
If CurrentUpTime < StoredUpTime
StoredUpTime = StoredUpTime + CurrentUpTime
Else
StoredUpTime = CurrentUpTime
EndIf
;Then write the value of the StoredUptime
PS. you want to write your stored up time in seconds not miliseconds or you will run into the same problem with the 49 day thing.
This is just a simple fix, but the way I'm storing the uptime is a little differn't. I store the houre, minutes, seconds, and miliseconds seperately. You would use code similar to above to compare each one. This method is the best i have found so far.
Posted: Sat Mar 21, 2009 2:48 pm
by PB
Does anyone know how to reliably get the PC's uptime without using
GetTickCount or ElapsedMilliseconds? Preferably with a short snippet.
I found this, is it easily convertable to PureBasic?
Code: Select all
Set objWMIService=GetObject("winmgmts:\\.\root\cimv2")
Set colOperatingSystems=objWMIService.ExecQuery _
("Select * From Win32_PerfFormattedData_PerfOS_System")
For Each objOS in colOperatingSystems
intSystemUptime=Int(objOS.SystemUpTime)
TimedAt=FormatDateTime(Date(),2) &", " &FormatDateTime(Time(),4)
Msgbox UpTime(intSystemUptime)
Next
Function UpTime(S)
M=S\60 : S=S mod 60 : H=M\60 : M=M mod 60 : D=H\24
UpTime=D &" Days, " & H MOD 24 &" Hours, " &M &" Minutes"
End Function
Posted: Sat Mar 21, 2009 3:51 pm
by netmaestro
This should be reliable on XP though slow:
Code: Select all
program = RunProgram("systeminfo.exe","","",#PB_Program_Open|#PB_Program_Read|#PB_Program_Hide)
While ProgramRunning(program)
If AvailableProgramOutput(program)
a$=ReadProgramString(program)
If FindString(a$, "System Up Time", 1)
uptime$ = a$
KillProgram(program)
EndIf
EndIf
Delay(1)
Wend
MessageRequester("",uptime$,$c0)
I'm sure it's located in the registry and you can just read it directly, so a little research might yield a faster proc. Not sure if it works on Vista or 7.
Posted: Sat Mar 21, 2009 3:57 pm
by netmaestro
There is also the GetSystemTimes_( ) API, which returns three times: idle time, kernel mode time and user time. iirc these are totals, so if you add them up they should equal uptime. But I haven't done it so I can't say for sure. If it works though, it's probably the best approach, better than reading the registry or running OS programs in the background.
Posted: Sat Mar 21, 2009 4:32 pm
by Sparkie
Using srod's COMate...
Code: Select all
XIncludeFile "COMate.pbi"
Procedure.s UpTime_Info()
Define.COMateObject objWMIService, UpTime
colUpTime.COMateEnumObject
strComputer.s = "."
objWMIService = COMate_GetObject("winmgmts:\\" + strComputer + "\root\cimv2", "")
If objWMIService
colUpTime = objWMIService\CreateEnumeration("ExecQuery('Select * from Win32_PerfFormattedData_PerfOS_System')")
If colUpTime
UpTime = colUpTime\GetNextObject()
myUpTime = UpTime\GetIntegerProperty("SystemUpTime")
uMinutes = myUpTime/60
uSeconds = myUpTime%60
uHours = uMinutes/60
uMinutes = uMinutes%60
uDays = uHours/24
upTimeDuration$ = Str(uDays) + " Days" + #crlf$
upTimeDuration$ + Str(uHours) + " Hours" + #crlf$
upTimeDuration$ + Str(uMinutes) + " Minutes" + #crlf$
upTimeDuration$ + Str(uSeconds) + " Seconds" + #crlf$
startUpTime = Date() - myUpTime
startUpTime$ = FormatDate("%mm/%dd/%yyyy %hh:%ii:%ss", startUpTime)
MessageRequester("System Up Since", startUpTime$ + #crlf$ + #crlf$ + upTimeDuration$)
UpTime\Release()
colUpTime\Release()
EndIf
objWMIService\Release()
EndIf
EndProcedure
UpTime_Info()
Posted: Sat Mar 21, 2009 4:50 pm
by Kwai chang caine
netmaestro wrote:This should be reliable on XP though slow:
Code: Select all
program = RunProgram("systeminfo.exe","","",#PB_Program_Open|#PB_Program_Read|#PB_Program_Hide)
While ProgramRunning(program)
If AvailableProgramOutput(program)
a$=ReadProgramString(program)
If FindString(a$, "System Up Time", 1)
uptime$ = a$
KillProgram(program)
EndIf
EndIf
Delay(1)
Wend
MessageRequester("",uptime$,$c0)
I'm sure it's located in the registry and you can just read it directly, so a little research might yield a faster proc. Not sure if it works on Vista or 7.
For info this code Return nothing at my home XP PRO SP2
@Sparkie
Your code works fine
Thanks at you two 
Posted: Sat Mar 21, 2009 5:03 pm
by PB
Thanks to Freak I was able to come up with this, which works perfectly:
Code: Select all
QueryPerformanceFrequency_(@perSec.q)
For a=1 To 10
QueryPerformanceCounter_(@currTime.q)
Debug FormatDate("%hh:%ii:%ss",currTime/perSec)
Sleep_(1000)
Next
No need for program outputs, Registry, COMate, etc.

Many thanks must
go to netmaestro and Sparkie for taking the time to post their solutions.
(BTW: I know this only works for 24 hours, but should be easy to enhance).