2010-11-30 11 views
7

Actualmente enfrentamos el problema de una llamada a WriteFile (o, mejor dicho, CFile :: Write - pero eso solo llama a WriteFile internamente) que causa el error de Win32 5ERROR_ACCESS_DENIED.¿Qué causa que WriteFile devuelva ERROR_ACCESS_DENIED?

(EDIT:.! Tenga en cuenta que no podemos repro el comportamiento Todo lo que tenemos en este momento es un archivo de registro que indica la línea fuente donde estaba el CFile :: Write y que contiene como un error ERROR_ACCESS_DENIED)

(EDIT : El archivo está en una unidad localy es, de hecho, un archivo y no un directorio)

Ahora, WriteFiles's documentation realmente no ayuda, y experimentando con un simple análisis de la aplicación arroja los siguientes resultados:.

  1. WriteFile causa ERROR_ACCESS_DENIED si se llama para un identificador de archivo que no está abierto para escritura (es decir está abierto solo para lectura).
  2. Se se no causa ERROR_ACCESS_DENIED si
    • El mango no es válido o el archivo no está abierto en todo
    • El acceso derechos, o la bandera protegida de escritura para el archivo se modifican después de el archivo ha sido abierto por el proceso. (Si éstos se modifican antes se abre el archivo, a continuación, nunca llegamos a WriteFile porque abrir el archivo fallará.)
    • El archivo es de alguna manera bloqueado por otro proceso/mango (esto en el mejor resultado en el error 32 ERROR_SHARING_VIOLATION)

Eso nos deja con la situación, que al parecer la única posibilidad de que esta llamada a fallar si el archivo se abrió en realidad con la bandera de lectura en lugar de la bandera de escritura. Sin embargo, al mirar nuestro código, esto parece extremadamente improbable. (Debido a nuestra localización, que podemos estar seguros de que WriteFile falló y que puede estar seguro de que el error es ERROR_ACCESS_DENIED, no podemos estar 100.1% seguro de las banderas de apertura, ya que estos no están trazadas.)

¿Hay alguna otra circunstancia conocida en la que WriteFile (CFile :: Write) cause un ERROR_ACCESS_DENIED?

Nota: Para aclarar, además, el contexto de esta pregunta:

  • El archivo se abierta, por lo tanto, no puede ser un directorio o algo por el estilo
  • Todas las pruebas que realicé indican que mientras el archivo está abierto, no se puede eliminar, por lo que el archivo debería haber estado allí en la llamada a WriteFile
  • El archivo está ubicado en una unidad local y no en una unidad de red.

debo añadir que estamos corriendo en Windows XP SP3 y la aplicación se compila con Visual Studio 2005.

+1

por qué no se puede rastrear las banderas de apertura? Si no desea editar el código, simplemente use el monitor de proceso para inspeccionarlos. –

+0

Claro que podemos agregar rastreo. Esto solo ocurre de vez en cuando en el sitio de un cliente. No hay manera de que podamos agregar un depurador allí. –

+1

Los controladores de filtro del sistema de archivos también pueden causar esto, el ejemplo más obvio son los escáneres antivirus (aunque hay otros como el cifrado, etc.). – Luke

Respuesta

3

La pregunta era

¿Qué causa la escritura de archivo para volver ERROR_ACCESS_DENIED?

y dije en la pregunta

  1. escritura de archivo causará ERROR_ACCESS_DENIED si se llama para un identificador de archivo que no está abierto para la escritura (es decir, se abre para sólo lectura) .

Después de añadir la tala de árboles para las banderas abiertos y otro incidente, resulta que esto era correcto. El registro de las banderas abiertas muestra que en el punto de error, el objeto de archivo se abrió con CFile :: modeRead y, por lo tanto, obtuvimos ERROR_ACCESS_DENIED.

Aún no descubrimos qué ruta de código extraña conduce a esto, pero esto solo muestra: Nunca confíes en tu propio código. :-)

(Ah, y por cierto. No fue ::WriteFile que falló, pero la API ::FlushFileBuffers, pero al parecer que devuelve el mismo error.)

+0

Si esto respondió tu propia pregunta, márcalo como tal. – RedX

+0

@RedX: Gracias. No lo hice de inmediato, porque pensé que las auto respuestas estaban bloqueadas por un tiempo determinado. Parece que esto se aplica a la edad de la pregunta y no a la respuesta. –

0

si se puede depurarlo, debería hacerlo. que podría ser un millón de cosas:

  • MSDN es incorrecto (que pasa mucho)
  • alguna aplicación (virus?) es conectar escritura de archivo y causando un comportamiento diferente
  • problema de sistema de archivos?
  • algo mal en su registro, o las observaciones
+2

En mi humilde opinión, esto debería haber sido un comentario.La depuración del problema no es posible en este momento. –

1

Hay alrededor de una docena de situaciones diferentes que pueden dar como resultado ERROR_ACCESS_DENIED. Internamente, todo lo que hace WriteFile es llamar a NtWriteFile y asignar su código de error (algo significativo) NTSTATUS a un HRESULT menos significativo.

Entre otras cosas, ERROR_ACCESS_DENIED podría indicar que el archivo está en un volumen de red y que algo salió mal con permisos de escritura, o que el archivo realmente no es un archivo sino un directorio.

+0

El archivo no está en un volumje de red y de hecho es un archivo. –

Cuestiones relacionadas