Abrí una imagen JPG con el bloc de notas, pegué todo el "texto" en un nuevo archivo de bloc de notas, cambié a .JPG y ya no se abre. ¿Por qué?

82

Este fenómeno me ha estado dejando preguntas para hacer.

Aquí está el experimento detallado, mi sistema operativo es Windows 7 x64 SP1:

  • Cambié un archivo de imagen (JPG) a TXT simplemente cambiando su extensión (o uno podría elegir abrir el JPG con el bloc de notas, lo mismo)

Debería verse así, secuencias de textos de aspecto extraño, y algunos de ellos (muy raros) son realmente significativos, como en la captura de pantalla siguiente "creador: dg-jpeg v1.0 ..."

Texto de muestra JPG

  • Inhabilité el ajuste y seleccioné todo el texto usando Ctrl + A (para asegurarme de que no se pierda nada)
  • Pegué el texto copiado en otro archivo TXT en blanco y lo guardé como JPG, comparé el nuevo tamaño del archivo con el JPG original. Todos ellos (el JPG original, el archivo TXT convertido y el archivo TXT recién creado) tienen exactamente el mismo tamaño, en bytes.

Cuando intenté abrir, Windows decía "Windows Photo Viewer no puede abrir esta imagen porque el archivo parece estar dañado, dañado o es demasiado grande" .

Incluso intenté probarlo con otro método: abrí el JPG con el bloc de notas, corté UN carácter conocido de una ubicación fácil de recordar (como el primer carácter de la segunda línea) y luego guardé el archivo. El espectador, por supuesto, mostraría el mismo mensaje. Luego lo abrí nuevamente y pegué el carácter en la ubicación EXACTA (el Bloc de notas recuerda su estado de salida, como la posición de las ventanas, el ajuste, el tamaño de las fuentes ... así que no tengo problemas para hacerlo correctamente)

Y sigue siendo el mismo error. Puede intentar esto para hacerse una idea, recuerde elegir una imagen pequeña, de lo contrario, el Bloc de notas actuará como un viejo oxidado.

¿Cuál pudo haber sido la causa de este fenómeno?

Nguyễn Tuấn Danh
fuente
44
Prueba el comando fc. abra un indicador de cmd y haga: C:\blah>fc file1 file2 es posible que los archivos sean del mismo tamaño pero diferentes. (aunque generalmente algún cambio aleatorio no tiende a dejar un archivo del mismo tamaño pero podría fácilmente). El comando fc te será muy útil para investigar lo que está sucediendo. También puede usar el comando xxd, esto está en cygwin y también viene con vim7. xxd -p file1 Eso volcará el hexadecimal de un archivo. Puede comparar el hexadecimal de los dos archivos con eso y fc. O incluso abra el hexadecimal en el bloc de notas y pase entre las dos ventanas del bloc de notas con la pestaña alt.
barlop
22
Está intentando leer un archivo binario con un editor de texto simple como el bloc de notas. No podrá leer la codificación ANSI correctamente y, por lo tanto, la convertirá. Cuando lo guarde, el archivo ya no será binario y, por lo tanto, el analizador no podrá leer los datos dentro del archivo. (Busque la diferencia entre guardar archivos basados ​​en XML y guardar archivos binarios es un tema interesante). Si intenta el mismo experimento con Notepad ++, tendrá éxito en lo que estaba intentando.
woutervs
3
Para los interesados: puede editar imágenes en Vim: sin embargo, el truco es que Vim convierte el archivo en formato XPM , que es ASCII simple.
Boldewyn
44
En pocas palabras, el Bloc de notas modifica su archivo antes de mostrárselo.
Derek 朕 會 功夫

Respuestas:

81

Dependiendo de la codificación utilizada para abrir el archivo, puede ver un comportamiento diferente. Mi bloc de notas de Windows 7 permite abrir un archivo en ANSI, UTF-8, Unicode o Unicode big endian.

He probado este problema con una pequeña imagen jpeg de 2x2 píxeles creada con gimp y abriendo y guardando el archivo de imagen con codificación ANSI. Al abrir tanto la imagen original como la guardada con un editor hexadecimal, veo que todas las secuencias 00 (dos dígitos hexadecimales, carácter de control NUL ) se han convertido a 20 (carácter de espacio).

Reemplazar de nuevo en el editor hexadecimal todo 20 por 00 restaura el formato de imagen.

Lo busqué en Google un poco y no encontré ninguna referencia que explique por qué lo hace. Solo una referencia a una publicación que advierte al respecto (enlace de caché de google, la página no está disponible).

Si guarda / abre el archivo como UTF-8, parece que todavía convierte los caracteres NUL en espacios, pero también aumenta el tamaño del archivo resultante debido a las conversiones de caracteres de un solo byte a secuencias de múltiples bytes UTF-8.

Si guarda / abre el archivo como Unicode, parece que todavía convierte los caracteres NUL en espacios, pero también agrega un byte al comienzo del archivo, la lista de materiales .

mangper
fuente
22
0x00 es un terminador de cadena en cadenas C. Es posible que los hayan reemplazado ya que un archivo de texto no debe contenerlos. El Bloc de notas es un programa muy antiguo.
Zonder
25
Dudo que notepad.exe sea un ejecutable .NET.
knittl
10
La cadena de CA @Bakuriu ciertamente puede existir en un archivo; Puedo pensar en numerosos formatos de archivo que los contienen. Y la gran mayoría de las aplicaciones que se envían con aplicaciones de Windows son nativas, no .NET. Dicho esto, el bloc de notas no escribe cadenas terminadas en nulo en los archivos.
Carey Gregory
44
@Bakuriu: los programas de Windows generalmente no están escritos en .Net. Es C / C ++ y nativo en el núcleo. Una de las aplicaciones .Net desarrolladas por Microsoft fue Live Writer, que ahora está descontinuada.
bhathiya-perera
55
@ SJuan76 ¿Eh? C ++ no define un tipo de datos llamado byte. Quizás estés pensando en otro idioma. Y los desarrolladores de aplicaciones pueden manejar datos binarios como les parezca, incluido el uso de cadenas C si así lo desean. Como dije antes, puedo pensar en numerosos formatos de archivos binarios que contienen cadenas C.
Carey Gregory
37

Por qué falla:

El bloc de notas crea espacios de (ASCII code 32)caracteres para caracteres como NUL (ASCII code 0) porque el cuadro de texto de la API de Windows solo permite char * ASCIIZ (matriz de caracteres, puntero) con terminación nula . Se corta en el primer NUL.

Eso sucede porque la API de Windows está escrita principalmente en lenguaje C y las cadenas terminadas en nulo son una de las características comunes. Incluso cuando Windows y Unicode modernos se consideran las mismas cadenas terminadas en nulo. Entonces, el bloc de notas simplemente reemplácelos con espacio para que pueda ver el archivo completo.

Entonces, cuando guarda el archivo, está dañado.

cadenas terminadas en nulo wikipedia


Cómo hacer más investigación:

Puedes usar un comparador como " compare" (comercial, de prueba) para ver el efecto de reemplazo del personaje. También vea otras herramientas de comparación binarias .

comparación hexadecimal

Nota : (20) 16 = (32) 10


La razón del bloc de notas actúa lentamente en archivos grandes

Comprueba cada carácter y reemplaza caracteres especiales con espacios. Otro software no realiza conversiones en memoria (al menos no primitivo como el bloc de notas). Simplemente representan caracteres especiales de manera diferente. Y utilizan técnicas avanzadas de almacenamiento en búfer.


Buscando en Notepad.exe (XP 32 bit)

(Supongo que todavía está escrito en C ++ o al menos usa un vinculador similar )

bloc

Estoy usando la herramienta PEiD (que detuvo el desarrollo con la introducción de PE + / 64 exes)

PEiD se puede encontrar incluido en la carpeta bin de Universal Extractor

Extraje el bloc de notas. ex_ archivo de la iso de Windows XP obviamente. Pruébalo. Es un extracto de un archivo cab usando 7z.

Advertencia ! Su escáner de virus podría detectar Universal Extractor / PEiD como herramientas de hackeo o virus. ¡No confíes en él, no lo descargues!


Más información sobre la API de Windows

créditos: Jason C

No es solo el cuadro de texto; WM_SETTEXT en general no proporciona ningún parámetro para especificar la longitud de la cadena, y siempre se supone que las cadenas terminan en nulo. Siempre puede crear un cuadro de texto personalizado con un mensaje personalizado que especifique la longitud de la cadena, pero el Bloc de notas y la mayoría de los otros programas razonablemente no lo hacen. Además, la función SetWindowText tampoco proporciona un parámetro de longitud.

bhathiya-perera
fuente
1
Es un poco extraño que muestre la hoja de propiedades de un ejecutable del Bloc de notas incluido con una versión de Windows XP, pero a juzgar por el tema de la ventana, claramente está ejecutando alguna versión de Windows 8. Eso explicaría por qué el ejecutable estaba vinculado con versión 7.1 del conjunto de herramientas: eso es lo que usaron para compilar Windows XP y las utilidades asociadas. La versión de Windows 8 del Bloc de notas, sin duda, se compilará con una versión más reciente de las herramientas del SDK.
Cody Gray
2
No es solo el cuadro de texto; WM_SETTEXTen general no proporciona ningún parámetro para especificar la longitud de la cadena, y siempre se supone que las cadenas terminan en nulo. Siempre puede crear un cuadro de texto personalizado con un mensaje personalizado que especifique la longitud de la cadena, pero el Bloc de notas y la mayoría de los otros programas razonablemente no lo hacen.
Jason C
@BhathiyaPerera Porque estoy satisfecho con el nivel de trabajo que he realizado al agregar información en un comentario. Si lo desea, puede mejorar su respuesta con esa información.
Jason C
28

El Bloc de notas no conserva todos los caracteres especiales / extendidos exactamente como son. No tengo una referencia para este comportamiento inmediatamente, pero he descubierto que este es el caso, por ejemplo, con el fin de línea LF de estilo UNIX, que el Bloc de notas convertirá en CRLF y nulo (0x00) que ignorará. En un archivo binario, como un JPG, es probable que haya ocurrencias aleatorias de los caracteres que Notepad no conserva. Pruebe su experimento con un editor compatible con HEX y debería funcionar entonces. Actualizaré mi respuesta si encuentro una buena referencia y una vez que haya probado un editor HEX.

Actualización: probé con algunos editores de programadores conocidos, pero solo uno de ellos funcionó de inmediato, HxD de Maël Hörz . Nunca usé HxD antes, pero lo encontré gracias a una respuesta a este artículo de Stack, Un complemento de visor / editor hexadecimal para Notepad ++ .

Los otros editores que no funcionaron después de unos minutos de esfuerzo fueron Notepad ++, Notepad2 y UltraEdit (v17.3, versión anterior). Un par de estos tuvo problemas con la copia / pegado de los primeros bytes, el número mágico de firma de archivo JPEG FF D8 FF. Tal vez trabajarían con un poco más de violín de lo que tengo tiempo en este momento.

JohnC
fuente
Sublime Text (2/3) abre automáticamente un archivo binario mostrándolo en formato hexadecimal. Como ejemplo, el inicio del archivo JPEG simplemente haciendo clic en "abrir": puu.sh/aaAVx/bd08dab46e.png
tomsmeding
3
En realidad, más a menudo que el bloc de notas convertirá LF a CRLF, dejará el LF como está y mostrará el texto como si no hubiera ningún salto de línea.
Moshe Katz
6

Solía ​​poder hacer esto con Write back in the day. Era un programa estándar en Windows 3.1 pero no recuerdo si Windows 95 lo incluyó. La escritura permitiría la edición segura binaria de cualquier archivo que pudiera abrir (probablemente un tamaño de archivo muy limitado). El Bloc de notas definitivamente no es seguro para los binarios (el texto sigue siendo el mismo, pero los bytes reales de los caracteres que no son de texto [por ejemplo, códigos de control] pueden cambiar), por lo que su ejemplo JPG no funciona. ¡Intenta obtener una copia de Write (y Windows muy antiguo) y prueba tu experimento nuevamente!

Según el artículo de Wikipedia "Windows Write", Write se incluyó hasta Windows NT 3.5. Fue reemplazado por Wordpad en Windows 95 en adelante. write.exetodavía estaba presente en el directorio de Windows, pero era simplemente un contenedor para abrir Wordpad.

CJ Dennis
fuente
5

Creo que no es tanto un problema de codificación sino también de juego de caracteres. El formato JPG es básicamente una secuencia de bytes. Por lo tanto, permite caracteres no imprimibles como NUL, ETX, STX, SOH, DLE, etc.

El Bloc de notas de Microsoft no puede mostrar esos caracteres no imprimibles. Puede mostrar marcadores de posición de algún tipo, como un espacio para un carácter nulo. Por lo tanto, abrir el archivo con el Bloc de notas no muestra el contenido real, sino el contenido descodificado por la codificación seleccionada (utf-8, utf-16, etc.) y mostrado por un determinado conjunto de caracteres (unicode, ascii, etc.) excluyendo personajes imprimibles

Al seleccionar todo el texto que se muestra y copiar el texto en el portapapeles, solo copia los caracteres imprimibles, incluidos los marcadores de posición. Por lo tanto, convierte automáticamente caracteres nulos en espacios e ignora por completo otros caracteres no imprimibles.

Básicamente, simplemente pierdes contenido haciéndolo de esta manera. Si utiliza un editor hexadecimal, copiará todo el contenido por completo.


Actualización: la respuesta de Bhathiya Pereras es correcta: https://superuser.com/a/782885/322784 Los caracteres no imprimibles no se ignoran al copiar texto en el portapapeles.

sbecker
fuente
Cada archivo es "básicamente una secuencia de bytes".
Jason C
1
@ JasonC No estaría de acuerdo. Si bien cada archivo se puede leer como una secuencia de bytes. Los archivos estructurados como los archivos XML no son legibles como una secuencia de datos. El contenido no sería válido hasta que se haya leído el final del archivo. Un corte en medio jpg sigue siendo válido y se puede mostrar. Solo falta la mitad de la imagen.
sbecker
Realmente no hay lugar para el desacuerdo sobre eso. :) XML es una secuencia de bytes como cualquier otra cosa, y XML (junto con la codificación de caracteres) define un formato para esos bytes. Ciertamente es legible como un flujo de datos. Ábralo en un editor hexadecimal, por ejemplo. Esa secuencia de datos resulta ser analizable como XML.
Jason C
@JasonC No puedo discutir con eso en realidad. :) Touché!
sbecker
2

El archivo JPEG contiene datos que no son de texto, excepto algunos campos, básicamente se encontrarán valores de bytes entre 0 y 255, especialmente en el área que representa la imagen comprimida codificada que contiene datos casi pseudoaleatorios.

Pero el Bloc de notas tratará los datos como texto ANSI de forma predeterminada, por lo que hará varias cosas que alterarán los datos originales, como:

  • reemplazar bytes mapeo de caracteres especiales / indefinidos / prohibidos ya que no tiene sentido para un texto ANSI válido

  • volver a codificar caracteres nulos, fin de línea y fin de secuencias de archivos a convenciones de Windows / DOS

Lo que significa que si edita y guarda los datos como texto, cambiará el jpeg en el mejor de los casos y lo hará inutilizable en el peor de los casos.

Dados9
fuente
"ANSI" no es técnicamente correcto , aunque se entiende comúnmente.
Jason C