2009-02-06 25 views
8

que estoy tratando de actualizar mi hora del sistema utilizando la siguiente:Cómo actualizar la fecha y/u hora del sistema mediante .NET

[StructLayout(LayoutKind.Sequential)] 
private struct SYSTEMTIME 
{ 
    public ushort wYear; 
    public ushort wMonth; 
    public ushort wDayOfWeek; 
    public ushort wDay; 
    public ushort wHour; 
    public ushort wMinute; 
    public ushort wSecond; 
    public ushort wMilliseconds; 
} 

[DllImport("kernel32.dll", EntryPoint = "GetSystemTime", SetLastError = true)] 
private extern static void Win32GetSystemTime(ref SYSTEMTIME lpSystemTime); 

[DllImport("kernel32.dll", EntryPoint = "SetSystemTime", SetLastError = true)] 
private extern static bool Win32SetSystemTime(ref SYSTEMTIME lpSystemTime); 

public void SetTime() 
{ 
    TimeSystem correctTime = new TimeSystem(); 
    DateTime sysTime = correctTime.GetSystemTime(); 
    // Call the native GetSystemTime method 
    // with the defined structure. 
    SYSTEMTIME systime = new SYSTEMTIME(); 
    Win32GetSystemTime(ref systime); 

    // Set the system clock ahead one hour. 
    systime.wYear = (ushort)sysTime.Year; 
    systime.wMonth = (ushort)sysTime.Month; 
    systime.wDayOfWeek = (ushort)sysTime.DayOfWeek; 
    systime.wDay = (ushort)sysTime.Day; 
    systime.wHour = (ushort)sysTime.Hour; 
    systime.wMinute = (ushort)sysTime.Minute; 
    systime.wSecond = (ushort)sysTime.Second; 
    systime.wMilliseconds = (ushort)sysTime.Millisecond; 

    Win32SetSystemTime(ref systime); 
} 

Cuando puedo depurar todo se ve bien y todos los valores son correctos, pero cuando se calles el Win32SetSystemTime (ref systime) el tiempo real del sistema (tiempo de visualización) no cambia y permanece igual. La parte extraña es que cuando llamo al Win32GetSystemTime (ref systime) me da la nueva hora actualizada. ¿Alguien puede ayudarme con esto?

+0

como veo, TimeSystem no es de la clase de sistema de base, ¿está seguro de que TimeSystem no cambian la ¿hora? intente comentar el Win32SetSystemTime (ref systime); línea – Avram

Respuesta

4

De acuerdo con el código que tiene allí, no está incrementando la hora. Parece que está configurando la hora de su sistema exactamente al mismo tiempo que cuando llamó a Win32GetSystemTime.

Probar:

systime.wHour = (ushort)(sysTime.Hour + 1); 
+0

Pero no quiero incrementar la hora. Quiero configurarlo para otro momento. – user62958

+0

El comentario del código en su código establece específicamente "establecer el reloj del sistema por delante una hora". No estás cambiando el tiempo de tu sistema simplemente porque no lo estás cambiando. Para configurarlo en otro momento, debe establecer la estructura que está enviando en el método a una hora diferente a la hora actual. –

6

Parte del problema es que usted tiene un par de firmas PInvoke incorrectas. El SetSystemTime más notable debería tener un valor de retorno no nulo. Aquí está la firma correcta

/// Return Type: BOOL->int 
    ///lpSystemTime: SYSTEMTIME* 
    [System.Runtime.InteropServices.DllImportAttribute("kernel32.dll", EntryPoint="SetSystemTime")] 
    [return: System.Runtime.InteropServices.MarshalAsAttribute(System.Runtime.InteropServices.UnmanagedType.Bool)] 
public static extern bool SetSystemTime([InAttribute()] ref SYSTEMTIME lpSystemTime) ; 

Mi sospecha es que la cerradura de un valor de retorno en mal estado de la pila y la función SetSystemTime esencialmente terminó con datos erróneos.

2
 

TimeSpan diffLocalTime = DateTime.Now - DateTime.UtcNow; 
SystemTime systemTime = new SystemTime(); 
systemTime.Second = ... 
systemTime.Minute =.... 
systemTime.Hour -= (ushort)(diffLocalTime.Hours + 1); // 00:59:59 I rounded as 1 hour 
bool result = SetSystemTime(ref systemTime); 
 

Esto usando Está funcionando correctamente para la zona horaria local.

1
[DllImport("Kernel32.dll")] 
public static extern bool SetLocalTime(ref StractData.Datetime.SYSTEMTIME Time); 
0

Has sólo un problema de los privilegios, cuando corro ese programa sin privilegios, que does'nt cambia la fecha, pero si lo hago clic derecho sobre el programa y haga clic en Ejecutar como administrador, funciona!

2

No hay necesidad de P/Invocar - hay una manera más simple (pero no muy conocida) disponible en el ensamblado Microsoft.VisualBasic. Si está en C#, simplemente recuerde agregar una referencia al mismo.

Puede usar la clase Microsoft.VisualBasic.DateAndTime para obtener y cambiar la fecha o la hora. Las propiedades Today y TimeOfDay tienen instaladores que realizarán los cambios en la fecha o la hora.

Aún necesita los privilegios correspondientes; consulte el enlace de la documentación de MSDN a continuación.

He aquí un ejemplo arbitrario para cambiar la hora:

public static void SetTimeToPast() 
{ 
    Microsoft.VisualBasic.DateAndTime.TimeOfDay = DateTime.Now.AddMinutes(-2); 
} 

referencia en MSDN: http://msdn.microsoft.com/en-us/library/microsoft.visualbasic.dateandtime(v=vs.110).aspx

+0

Para mí, cambiar la fecha del sistema Microsoft.VisualBasic.DateAndTime.TimeOfDay.Today = [new Date] hizo el truco. Muchas gracias. Esta es hasta ahora la solución más fácil y limpia. – FrenkyB

+0

El uso de Win32SetSystemTime funciona para mí, pero lamentablemente esto no funciona. – Matt

Cuestiones relacionadas