2010-10-22 13 views
11

Deseo implementar IPC usando memoria compartida con nombre.Error del sistema 0x5: CreateFileMapping()

Para ello, uno de los pasos es conseguir un identificador de un objeto de memoria Mapeo, utilizando CreateFileMapping().

lo hago exactamente como el sitio web de MSDN reccommends: http://msdn.microsoft.com/en-us/library/aa366551(v=VS.85).aspx:

hFileMappingHandle = CreateFileMapping 
    (
     INVALID_HANDLE_VALUE,  // use paging file 
     NULL,      // default security 
     PAGE_READWRITE,   // read/write access 
     0,   // maximum object size (high-order DWORD) 
     256,   // maximum object size (low-order DWORD) 
     "Global\\MyFileMappingObject"   // name of mapping object 
    ); 
DWORD dwError = GetLastError(); 

Sin embargo, el mango devuelto es siempre 0x0, y el código de error Sistema devuelto es: 0x5 (Acceso denegado.)

  • Sólo la memoria nombrada Compartiendo deseado (no compartir archivos).
  • de Windows 7 x64 OS
  • derechos de usuario del administrador de bits disponibles
  • aplicación desarrollada: 64 bits aplicación plug-in (.dll)

¿Alguien tiene la misma experiencia, y una forma de arreglarlo, por favor? Utilizo el sitio de MSDN como mi referencia, por lo que no creo que haya un problema en el código.

+0

No estoy seguro de que sea el motivo, pero ¿no necesita establecer el tamaño máximo de objeto para que sea un múltiplo de la página de memoria (4096 bytes)? –

+1

Hola Eugene, no, el problema fue que no configuré SeCreateGlobalPriviledge. –

Respuesta

8

Parece que no tiene suficientes privilegios.

De MSDN:

Creación de un objeto de asignación de archivos en el espacio de nombres global de una sesión otra de sesión de cero requiere la SeCreateGlobalPrivilege privilegio. Para más información, vea Kernel Object Namespaces.

...

La creación de un objeto de asignación de archivos en el espacio de nombres global, mediante el uso de CreateFileMapping, de una sesión aparte de sesión de cero es una operación privilegiada . Debido a esto, una aplicación que se ejecuta en un Escritorio remoto Host de sesión arbitraria (RD Host de sesión) sesión de servidor debe tener SeCreateGlobalPrivilege habilitar fin de crear un objeto de asignación de archivos en el espacio de nombres global con éxito. La comprobación de privilegios se limita a la creación de objetos de asignación de archivos, y no se aplica a la apertura de los existentes . Por ejemplo, si un servicio o el sistema crea un objeto de mapeo de archivos, cualquier proceso que se ejecute en cualquier sesión puede acceder a ese objeto de mapeo de archivos siempre que el usuario tenga el acceso necesario .

+2

Hola Eugene, ese era exactamente mi problema. Eliminé el prefijo "Global \\" del nombre de mi objeto de mapeo, y al parecer eso solucionó el problema. No planeo tratar con servicios de terminal, por lo que la solución debería ser aceptable por ahora. Leí la documentación en SeCreateGlobalPriviledge, pero no está claro para mí, si la aplicación puede asignar los privilegios, o si tengo que ajustar manualmente los privilegios dicen desde Windows Explorer? –

+1

El privilegio se define por la cuenta de usuario con la que se inicia su aplicación. Puede intentar utilizar la función AdjustTokenPrivilege como se explica aquí: http://delphi.about.com/b/2008/09/26/zarko-needs-help-createfilemapping-terminal-services-global-session-secreateglobalprivilege.htm, pero esto no garantiza el resultado. En general, intente buscar SeCreateGlobalPrivilege, los resultados contienen algunas fuentes de información interesantes –

1

Para crear asignaciones de archivos globales necesita el privilegio SeCreateGlobalPrivilege - ¿lo tiene? Acceso denegado implica que este es un problema de permisos, seguro.

+0

Hola Steve, ese era mi problema. Gracias. Solucioné el problema por ahora de una manera diferente, pero si deseo establecer privilegios, ¿puedo hacerlo programáticamente desde mi aplicación, por favor? –

+0

Puede hacer esto usando 'AdjustTokenPrivileges' como se muestra aquí: http://msdn.microsoft.com/en-us/library/aa446619(v=VS.85).aspx. El manejador de token proviene de 'OpenProcessToken' que se debe llamar utilizando (al menos)' TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY' –

+0

Muchas gracias. –

2

Los administradores, servicios y servicios de red tienen SeCreateGlobalPrivilege de forma predeterminada. Sin embargo, debes recordar que Windows7/Vista no ejecuta todo como administrador. Por lo tanto, utilice "Comenzar como administrador" para que funcione "Global" para su aplicación. Si está depurando, inicie Visual Studio también como administrador.

+0

¡Muchas gracias! Visual Studio en Windows 10 no es administrador por defecto. Ese fue mi problema –

0

La referencia a los servicios de terminal en la documentación sobre el espacio de nombres global es un poco engañosa, ya que implica que solo tiene que preocuparse por esto si tiene una situación inusual. De hecho, tanto IIS como los servicios del sistema se ejecutan en la sesión cero, y el primer/único usuario que inicia sesión se ejecuta en la sesión 1, por lo que debe usar el espacio de nombres Global para comunicarse entre IIS o un servicio y un programa normal.

Cuestiones relacionadas