Saturday, June 5, 2010

Change System Time

To change or read the clock of the pc, the .Net framework provides no in-house version. But with all .Net languages the functions of the Win32-API can be used.
The Win32-API is a very mighty programming interface, which provides functions for programming for Windows.
The mostly systemclose functions are all written in C or Assembler and are saved in dll - files.
Luckily, there also is a function to manage the system time, which we can include in our C# - application. The including of external functions is called Platform Invoke (P/Invoke).
Now to the code:
To be able to include DLLs, the following using - directive is necessary:
using System.Runtime.InteropServices;

The external function to set the system time is made known to the program eventually as follows:

[DllImport("kernel32.dll", SetLastError = true)]
static extern bool SetSystemTime(ref str_Zeit neueZeit);

The function SetSystemTime() then can be called as a normal function. As parameter it expects an object of the type of the structure str_Zeit, which we define ourselves:
struct str_Zeit
        {
            public ushort Jahr; // year
            public ushort Monat; // month
            public ushort TagInDerWoche; // day in week
            public ushort Tag; // day
            public ushort Stunde; // hour
            public ushort Minute; // minute
            public ushort Sekunde; // second
            public ushort Millisekunde; // millisecond
        }
This structure is a replication of the type which the function expects - every structure with 8 unsigned 16-bit integers suffices the requirement.
The complete code could finally look like this (a call of the function SetzeSystemzeit() with a date object as parameter changes the system time to the given value):

public class ZeitSetzen
    {
        struct str_Zeit
        {
            public ushort Jahr;
            public ushort Monat;
            public ushort TagInDerWoche;
            public ushort Tag;
            public ushort Stunde;
            public ushort Minute;
            public ushort Sekunde;
            public ushort Millisekunde;
        }

        [DllImport("kernel32.dll", SetLastError = true)]
        static extern bool SetSystemTime(ref str_Zeit neueZeit);

        public void SetzeSystemzeit(DateTime neueZeit)
        {
            str_Zeit Zeit = new str_Zeit();
            Zeit.Jahr = (ushort)neueZeit.Year;
            Zeit.Monat = (ushort)neueZeit.Month;
            Zeit.TagInDerWoche = (ushort)neueZeit.DayOfWeek;
            Zeit.Tag = (ushort)neueZeit.Day;
            Zeit.Stunde = (ushort)neueZeit.Hour;
            Zeit.Minute = (ushort)neueZeit.Minute;
            Zeit.Sekunde = (ushort)neueZeit.Second;
            Zeit.Millisekunde = (ushort)neueZeit.Millisecond;
          
            SetSystemTime(ref Zeit);
        }
    }
Be careful when using Windows Vista, 7 and 8: To change the system time the program needs administrative rights. How that can be achieved, is explained in this post.

No comments:

Post a Comment