¿Por qué existe el límite de longitud de ruta de 260 caracteres en Windows?

390

Me he encontrado con este problema varias veces en momentos inoportunos:

  • Intentando trabajar en proyectos Java de código abierto con rutas profundas
  • Almacenar árboles wiki de Fitnesse profundos en el control de fuente
  • Un error al intentar usar Bazaar para importar mi árbol de control de código fuente

¿Por qué existe este límite?

¿Por qué no se ha eliminado todavía?

¿Cómo afrontas el límite del camino? Y no, cambiar a Linux o Mac OS X no es una respuesta válida a esta pregunta;)

Jeffrey Cameron
fuente
8
@Artelius: En realidad, Windows (al menos desde Win2K en adelante) admite puntos de unión ( en.wikipedia.org/wiki/NTFS_junction_point ), y Vista en adelante admite enlaces simbólicos NT ( en.wikipedia.org/wiki/NTFS_symbolic_link ). De todos modos, si bien los enlaces simbólicos pueden ayudar a hacer que las rutas más largas / anidadas sean más amigables, no puedo pensar cómo los enlaces simbólicos ayudarían si estás alcanzando los límites de longitud de la ruta.
Ashutosh Mehra
8
Incluso si este límite no existiera, siempre hay muchos otros límites, y cada uno de ellos podría ser molesto en algún momento. El punto es ¿por qué este límite es tan bajo? Después de la era de 8.3, y con hardware de tamaño mega / giga, una ruta ahora debería ser una cadena asignada dinámicamente con un tamaño prácticamente ilimitado.
Roland
12
Microsoft finalmente está resolviendo este problema, en Windows 10 Build 14352.
Warren P
3
Sí, y parece que tiene que modificar el manifiesto de la aplicación para que tenga en cuenta la ruta larga.
Warren P
3
@PatrickSzalapski por desgracia, se fijó visualstudio.uservoice.com/forums/121579-visual-studio/...
phuclv

Respuestas:

231

Citando este artículo https://docs.microsoft.com/en-us/windows/desktop/FileIO/naming-a-file#maximum-path-length-limitation

Limitación máxima de la longitud del camino

En la API de Windows (con algunas excepciones discutidas en los siguientes párrafos), la longitud máxima para una ruta es MAX_PATH , que se define como 260 caracteres. Una ruta local se estructura en el siguiente orden: letra de unidad, dos puntos, barra diagonal inversa, componentes de nombre separados por barras diagonales inversas y un carácter nulo de terminación. Por ejemplo, la ruta máxima en la unidad D es "D: \ alguna cadena de ruta de 256 caracteres <NUL>" donde "<NUL>" representa el carácter nulo de terminación invisible para la página de códigos del sistema actual. (Los caracteres <> se usan aquí para mayor claridad visual y no pueden ser parte de una cadena de ruta válida).

Ahora vemos que es 1 + 2 + 256 + 1 o [unidad] [: \] [ruta] [nulo] = 260. Se podría suponer que 256 es una longitud de cadena fija razonable de los días de DOS. Y volviendo a las API de DOS, nos damos cuenta de que el sistema rastreó la ruta actual por unidad, y tenemos 26 (32 con símbolos) unidades máximas (y directorios actuales).

El INT 0x21 AH = 0x47 dice "Esta función devuelve la descripción de la ruta sin la letra de unidad y la barra invertida inicial". Entonces, vemos que el sistema almacena el CWD como un par (unidad, ruta) y usted solicita la ruta especificando la unidad (1 = A, 2 = B, ...), si especifica un 0, entonces asume la ruta para la unidad devuelta por INT 0x21 AH = 0x15 AL = 0x19. Entonces, ahora sabemos por qué es 260 y no 256, porque esos 4 bytes no están almacenados en la cadena de ruta.

Por qué una cadena de ruta de 256 bytes, porque 640K es suficiente RAM.

valli
fuente
21
La API de Windows limita la longitud, incluso en el último sistema operativo. Microsoft tiene miedo de romper cientos de millones de sistemas operativos en uso hoy si esto cambiara porque ya no tienen genios trabajando para ellos que entiendan la API por dentro y por fuera, como lo hicieron en las décadas de 1980 y 1990. No vale la pena cambiar el riesgo. serverfault.com/questions/163419/…
MacGyver
77
@ MacGyver Lo siento, pero eso no tiene sentido. Microsoft no quiere romper los millones de aplicaciones mal escritas que asumen cosas sobre el sistema que nunca fueron garantizadas. Desafortunadamente, las cosas fueron de la misma manera durante tanto tiempo que los desarrolladores comenzaron a confiar en ellos, por lo que cambiarlo ahora rompería las aplicaciones de terceros y MS tendría la culpa.
Básico
25
por cierto, no hay pruebas de que Gates haya dicho alguna vez que "640K Ram es suficiente para todos" computerworld.com/article/2534312
Patrick Favre
11
@Basic El límite de 260 caracteres fue garantizado por Windows. La constante se declaró como una constante , se declaró una estructura en los archivos de encabezado de Windows que solo tiene espacio para 260 caracteres. No hay forma de cambiarlo.
Ian Boyd
35
@Basic La constante no cambia una vez que se compila en mi aplicación. Ejecuté una aplicación que se creó por última vez en 1994, y todavía se ejecuta hoy en Windows 10. Microsoft prometió un cierto tamaño binario de un bloque de memoria, y el programador siguió esa regla. Si Microsoft cambiara la constante, entonces todas las aplicaciones existentes, que siguieron correctamente la API de programación, se romperían . No puedes romper la compatibilidad binaria.
Ian Boyd
150

Esto no es estrictamente cierto ya que el sistema de archivos NTFS admite rutas de hasta 32k caracteres. Puede usar la api win32 y el \\?\prefijo " " de la ruta para usar más de 260 caracteres.

Una explicación detallada del largo camino del blog del equipo .Net BCL .
Un pequeño extracto resalta el problema con caminos largos

Otra preocupación es el comportamiento inconsistente que resultaría al exponer el soporte de ruta larga. Las rutas largas con el \\?\prefijo se pueden usar en la mayoría de las API de Windows relacionadas con archivos, pero no en todas las API de Windows. Por ejemplo, LoadLibrary, que asigna un módulo a la dirección del proceso de llamada, falla si el nombre del archivo es más largo que MAX_PATH. Esto significa que MoveFile le permitirá mover una DLL a una ubicación tal que su ruta tenga más de 260 caracteres, pero cuando intente cargar la DLL, fallará. Hay ejemplos similares en todas las API de Windows; existen algunas soluciones, pero son caso por caso.

softveda
fuente
44
Es justo, pero significa que debe usar P / Invoke en muchos lugares y esto, en mi opinión, reduce la portabilidad de su código .Net. ¿Qué pasa si quisiera mantener la compatibilidad mono?
Jeffrey Cameron
1
Mi punto era que puedes usar el camino largo si realmente lo deseas. Pero estoy de acuerdo en que es un dolor y personalmente también lo evitaría.
softveda
55
Esta debería ser la respuesta elegida. En realidad responde la pregunta planteada por el usuario de POR QUÉ existe este límite Y proporciona una solución alternativa. Upvote para la visibilidad
KyleMit
2
Me parece que Microsoft necesita arreglar sus API, y supongo que esto no es una prioridad. Me sorprendió que este límite todavía exista en Windows 8.
Mas
3
@Mas La "solución" que desea se realizó de nuevo a Windows XP. Llamar a la versión unicode de su API le permitirá acceder a la "ruta extendida". Creo que el explorador maneja esto automáticamente. Aquí hay una de esas funciones que lo admite: msdn.microsoft.com/en-us/library/windows/desktop/… .
Natalie Adams
108

La pregunta es por qué todavía existe la limitación. Sin duda, Windows moderno puede aumentar el lado de MAX_PATHpermitir caminos más largos. ¿Por qué no se ha eliminado la limitación?

  • La razón por la que no se puede eliminar es que Windows prometió que nunca cambiaría.

A través del contrato de API, Windows ha garantizado a todas las aplicaciones que las API de archivos estándar nunca devolverán una ruta más larga que los 260caracteres.

Considere el siguiente código correcto :

WIN32_FIND_DATA findData;

FindFirstFile("C:\Contoso\*", ref findData);

Windows garantizó a mi programa que llenaría mi WIN32_FIND_DATAestructura:

WIN32_FIND_DATA {
   DWORD    dwFileAttributes;
   FILETIME ftCreationTime;
   FILETIME ftLastAccessTime;
   FILETIME ftLastWriteTime;
   //...
   TCHAR    cFileName[MAX_PATH];
   //..
}

Mi aplicación no declaró el valor de la constante MAX_PATH, lo hizo la API de Windows. Mi aplicación usó ese valor definido.

Mi estructura está definida correctamente y solo asigna 592bytes en total. Eso significa que solo puedo recibir un nombre de archivo con menos de 260caracteres. Windows me prometió que si escribía mi aplicación correctamente, mi aplicación continuaría funcionando en el futuro.

Si Windows permitiera nombres de archivo más largos que 260caracteres, entonces mi aplicación existente (que usaba la API correcta correctamente) fallaría.

Para cualquiera que llame a Microsoft para cambiar la MAX_PATHconstante, primero deben asegurarse de que ninguna aplicación existente falle. Por ejemplo, todavía poseo y uso una aplicación de Windows que se escribió para ejecutarse en Windows 3.11. Todavía se ejecuta en Windows 10 de 64 bits. Eso es lo que le brinda la compatibilidad con versiones anteriores.

Microsoft hizo crear una manera de utilizar los 32.768 nombres completos de rutas; pero tuvieron que crear un nuevo contrato de API para hacerlo. Por un lado, debe usar la API de Shell para enumerar archivos (ya que no todos los archivos existen en un disco duro o recurso compartido de red).

Pero también tienen que no romper las aplicaciones de usuario existentes. La gran mayoría de las aplicaciones no utilizan la API de shell para el trabajo de archivos. Todos simplemente llaman FindFirstFile/ FindNextFiley lo llaman un día.

Ian Boyd
fuente
44
@JosiahKeller Si lo hiciera, rompería el contrato originalmente definido para ese método, y al hacerlo podría sobrescribir la memoria involuntaria y abrir potencialmente un agujero de seguridad. La única forma de solucionar esto es ofrecer una nueva API mejorada (como las variantes compatibles con Unicode) y esperar que todos recompilen y vuelvan a publicar todas sus aplicaciones utilizando la API más nueva.
Rowland Shaw
2
@Ryios No creo que mis aplicaciones existentes de Windows se ejecuten en Linux.
Ian Boyd
99
La compatibilidad con versiones anteriores es agradable. Pero creo que evitar estos problemas (a menudo realmente desagradables) hoy es más importante que admitir aplicaciones de Windows 3.1. ¿Cuántas personas tienen problemas con los caminos largos? ¿Y cuántas personas aún usan las aplicaciones de Windows 3.1? Incluso cancelaron el soporte para Windows XP. Entonces, ¿por qué no simplemente hacen un anuncio, que desde Windows [x] y aplicaciones posteriores que asumen que no habrá una ruta de más de 260 caracteres, no funcionarán como se esperaba cuando encuentran una ruta que es demasiado larga? Nuestros límites de velocidad tampoco tienen en cuenta los carruajes.
JuSchu
2
@JuSchu No son solo aplicaciones de Windows 3.1. Las aplicaciones escritas hoy usando la API correcta no funcionarán.
Ian Boyd
62

Desde Windows 10. puede eliminar la limitación modificando una clave de registro.

Consejo A partir de Windows 10, versión 1607, las limitaciones de MAX_PATH se han eliminado de las funciones comunes de archivos y directorios de Win32. Sin embargo, debe optar por el nuevo comportamiento.

Una clave de registro le permite habilitar o deshabilitar el nuevo comportamiento de ruta larga. Para habilitar el comportamiento de ruta larga, establezca la clave de registro en HKLM\SYSTEM\CurrentControlSet\Control\FileSystem LongPathsEnabled(Tipo:) REG_DWORD. El sistema almacenará en caché el valor de la clave (por proceso) después de la primera llamada a un archivo Win32 o función de directorio afectados (la lista sigue). La clave de registro no se volverá a cargar durante la vida útil del proceso. Para que todas las aplicaciones en el sistema reconozcan el valor de la clave, es posible que sea necesario reiniciar porque algunos procesos pueden haberse iniciado antes de configurar la clave. La clave de registro también se puede controlar mediante la Política de grupo en Computer Configuration > Administrative Templates > System > Filesystem > Enable NTFS long paths. También puede habilitar el nuevo comportamiento de ruta larga por aplicación a través del manifiesto:

<application xmlns="urn:schemas-microsoft-com:asm.v3">
    <windowsSettings xmlns:ws2="http://schemas.microsoft.com/SMI/2016/WindowsSettings">
        <ws2:longPathAware>true</ws2:longPathAware>
    </windowsSettings>
</application>
Root Loop
fuente
15
Lamentablemente, incluso en la última versión Win10, el Explorador de archivos en sí todavía tiene problemas para tratar con el nombre de ruta larga. Incluso "Copiar como ruta" en el menú contextual no funciona como se esperaba; solo copia los primeros 260 caracteres. No puede crear una carpeta, copiar / mover / abrir un archivo ... Haga que me pregunte cuál es el punto de este cambio.
raymai97
Tenga en cuenta que la afirmación de que la configuración del sistema es independiente de la configuración del manifiesto es incorrecta. Ambos son obligatorios. La política debe habilitarse en el nivel del sistema y el manifiesto debe declarar que la aplicación reconoce la ruta larga.
Eryk dom
Leí que hacer este cambio podría causar problemas de compatibilidad con aplicaciones antiguas de 32 bits, pero ¿es común este tipo de problema con la compatibilidad? Me gustaría hacer el cambio yo mismo. lifehacker.com/…
KDP
32

Puede montar una carpeta como unidad. Desde la línea de comando, si tiene una ruta C:\path\to\long\folder, puede asignarla a la letra de unidad X:usando:

subst x: \path\to\long\folder
jonchang
fuente
Estoy recibiendo "Parámetros inválidos j:" al intentar este comando
barrypicker
Esto debe ejecutarse desde un símbolo del sistema Administrador (elevado).
Mrchief
Esto fallará con las barras diagonales, debe ser una barra diagonal inversa.
cchamberlain
1
No estoy seguro de si esto se aplica solo a Windows 10, sin embargo, acabo de encontrar que cuando intento ejecutar este comando, si ejecuto como administrador como se sugirió anteriormente, la unidad no parece estar disponible. Esto se debe a que el comportamiento parece ser similar a la asignación de una unidad de red y es específica de la sesión, etc., por lo que cuando ejecuté como administrador y usé este comando, esa sesión podría usar x: TL; DR Si no puede ver la unidad, intente ejecutar el comando sin estar en modo administrador.
Jaddie
substes local-session / account - vea superuser.com/questions/29072/… para saber cómo hacerlo 'en todo el sistema'
usuario2864740
18

Una forma de hacer frente al límite de ruta es acortar las entradas de ruta con enlaces simbólicos.

Por ejemplo:

  1. crear un C:\pdirectorio para mantener enlaces cortos a rutas largas
  2. mklink /J C:\p\foo C:\Some\Crazy\Long\Path\foo
  3. agregar C:\p\fooa su ruta en lugar de la ruta larga
JDiMatteo
fuente
3
No tuve que crear el directorio primero, por lo que el paso 1 no es necesario.
ohaal
2
Este truco no siempre funciona, ya que muchas aplicaciones intentan resolver los enlaces
nponeccop
La /jopción crea un punto de montaje de unión para un dispositivo de volumen local o una ruta en un volumen local (como un montaje de enlace Unix). No crea un enlace simbólico. Es una distinción importante ya que los puntos de montaje de unión siempre se evalúan en un servidor y deben apuntar a dispositivos locales, mientras que los enlaces simbólicos se evalúan en el cliente y pueden apuntar a rutas remotas (si lo permite la política). Al igual que una unidad subst.exe (es decir DefineDosDeviceW), un objetivo de unión generalmente está limitado a unos 4 k caracteres. En realidad, son 8K caracteres, divididos de manera uniforme entre la ruta de sustitución y la ruta de visualización.
Eryk dom
12

Puede habilitar nombres de ruta largos con PowerShell:

Set-ItemProperty -Path 'HKLM:\SYSTEM\CurrentControlSet\Control\FileSystem' -Name LongPathsEnabled -Type DWord -Value 1 

Otra versión es usar una Política de grupo en Computer Configuration/ Administrative Templates/ System/ Filesystem:

Editor de políticas de grupo

MovGP0
fuente
2
Cada aplicación todavía tiene que declarar que es consciente de la ruta larga. Microsoft ha hecho un mal trabajo al comunicar esto al hacer que parezca que el manifiesto de la aplicación es solo otra forma de habilitar esta función, en lugar de explicar claramente que es un contrato entre el SO (política de nivel del sistema) y la aplicación en la que ambos tienen que estar de acuerdo.
Eryk dom
8

En cuanto a por qué esto todavía existe: MS no lo considera una prioridad y valora la compatibilidad con versiones anteriores sobre el avance de su sistema operativo (al menos en este caso).

Una solución alternativa que uso es usar los "nombres cortos" para los directorios en la ruta, en lugar de sus versiones estándar legibles por humanos. Así , por ejemplo, para C:\Program Files\que yo usaría C:\PROGRA~1\ Usted puede encontrar los equivalentes de nombre corto utilizando dir /x.

Conrad
fuente
1
Los nombres de ruta cortos se pueden deshabilitar en el registro (¿o fue el sistema de archivos en sí mismo?), Por lo que esto realmente no es una solución confiable.
rubenvb
3
@rubenvb Estoy seguro de que la mayoría de las funciones de Windows, si no todas, se pueden deshabilitar en el registro, así que ¯ \ _ (ツ) _ / ¯
Conrad el
La generación de nombres cortos se puede deshabilitar para NTFS (y debería serlo porque es ineficiente en muchos casos), ya sea para todo el sistema o por volumen, por lo que es un enfoque poco confiable incluso para rutas en la unidad del sistema, que debe ser NTFS. Es posible establecer manualmente nombres cortos en archivos y directorios en NTFS, pero esto no se extiende a los sistemas de archivos más nuevos que no admiten nombres cortos, como exFAT y ReFS. Los nombres cortos deben considerarse una característica obsoleta que se mantiene por compatibilidad en casos limitados, como la antigua API ANSI / OEM que usa páginas de códigos de uno y dos bytes.
Eryk Sun
@eryksun Consulte mi comentario anterior sobre la desactivación de nombres de ruta cortos. :) Solo porque creas que debería considerarse obsoleto, no significa que en realidad lo sea. MS no tiene planes de desaprobar esta característica. (Además, ¿por qué está instalando el software de Windows en particiones exFAT / ReFS?)
Conrad
Todavía digo que solo use rutas de dispositivo no normalizadas (es decir, el prefijo "\\? \"), Ya que siempre están disponibles y son obvias. Por ejemplo, traduzca PATHy páselo a SearchPathW. También es eficiente, ya que la biblioteca en tiempo de ejecución crea rutas de dispositivo "\\? \" Para NT de todos modos. En cuanto a los sistemas de archivos más nuevos, probablemente no veríamos el software instalado en un volumen exFAT, que no sea aplicaciones portátiles, ya que no tiene seguridad, pero no descartaría ReFS. Los usuarios instalan programas en ubicaciones no estándar por razones de conveniencia, espacio o rendimiento.
Eryk Sun
7

En cuanto a cómo hacer frente a la limitación de tamaño de ruta en Windows: usar 7zip para empacar (y desempaquetar) sus archivos confidenciales de longitud de ruta parece una solución viable. Lo he usado para transportar varias instalaciones IDE (esas rutas de complementos de Eclipse, ¡ay!) Y montones de documentación autogenerada y hasta ahora no he tenido un solo problema.

No estoy seguro de cómo evade el límite de 260 caracteres establecido por Windows (desde un punto de vista técnico), pero bueno, ¡funciona!

Más detalles en su página de SourceForge aquí :

"NTFS puede admitir nombres de ruta de hasta 32,000 caracteres de longitud".

7-zip también admite nombres tan largos.

Pero está deshabilitado en el código SFX. A algunos usuarios no les gustan los caminos largos, ya que no entienden cómo trabajar con ellos. Es por eso que lo he deshabilitado en el código SFX.

y notas de lanzamiento :

9.32 alfa 01/12/2013

  • Soporte mejorado para nombres de ruta de archivo de más de 260 caracteres.

4.44 beta 2007-01-20

  • 7-Zip ahora admite nombres de ruta de archivo de más de 260 caracteres.

NOTA IMPORTANTE: Para que esto funcione correctamente, deberá especificar la ruta de destino en el cuadro de diálogo "Extraer" de 7zip directamente, en lugar de arrastrar y soltar los archivos en la carpeta deseada. De lo contrario, la carpeta "Temp" se usará como caché provisional y rebotará en la misma limitación de 260 caracteres una vez que el Explorador de Windows comience a mover los archivos a su "lugar de descanso final". Consulte las respuestas a esta pregunta para obtener más información.

Priidu Neemre
fuente
3
Me equivoqué, 7zip y WinRAR extraen todas las carpetas y archivos. Es solo que la propiedad de una carpeta en Windows solo informa el número de carpetas y archivos que no violan la limitación. Es como si el Explorador de Windows no profundizara más para descubrir carpetas cuando se alcanza la ruta máxima.
Twisted Whisper
Es posible eliminar una ruta larga en 7-zip con shift-del.
Laurie Stearn
Respuesta corta: use 7zip para descomprimir un archivo .zip ... funcionó para mí en Windows 7
andrewcockerham
2

Otra forma de lidiar con esto es usar Cygwin, dependiendo de lo que desee hacer con los archivos (es decir, si los comandos de Cygwin se adaptan a sus necesidades)

Por ejemplo, permite copiar, mover o renombrar archivos que incluso el Explorador de Windows no puede. O, por supuesto, lidiar con su contenido como md5sum, grep, gzip, etc.

También para los programas que está codificando, podría vincularlos a la DLL de Cygwin y les permitiría usar rutas largas (aunque no he probado esto)

eliblanco87
fuente