Passer au contenu principal

Si vous avez déjà essayé d'utiliser des programmes basés sur POSIX pour traiter des fichiers structurés VOS, vous avez peut-être rencontré certaines restrictions ou observé des comportements que vous ne compreniez pas. Dans cet article, je vais tenter d'expliquer ce qui se passe.

VOS prend en charge quatre types de fichiers : séquentiels, relatifs, fixes et en flux. Les trois premiers formats sont appelés fichiers « structurés », car le système de fichiers garde la trace des limites des enregistrements. Les opérations d'E/S disponibles permettent de lire et d'écrire des enregistrements entiers. Le dernier format est appelé « non structuré », car les limites des enregistrements sont implicites ; c'est le caractère de nouvelle ligne qui délimite les enregistrements. Les opérations d'E/S disponibles permettent de lire et d'écrire des séquences d'octets.

Un environnement conforme à la norme POSIX, tel qu'on le trouve sur un système Unix® ou Linux©, ne dispose que d'un seul type de fichier natif, appelé « fichier ordinaire ». L'organisation des fichiers en flux VOS équivaut à celle d'un fichier ordinaire POSIX.

L'environnement d'exécution VOS POSIX classe ces quatre types de fichiers comme des fichiers réguliers POSIX. Ainsi, du moins en théorie, tout programme POSIX peut lire ou écrire n'importe lequel de ces quatre types de fichiers. Cependant, ce n'est pas aussi simple que cela.

Étant donné que l'API POSIX définit toutes les opérations d'E/S en termes de séquences d'octets, tandis que VOS définit les opérations d'E/S (sur des fichiers structurés) en termes de séquences d'enregistrements, le moteur d'exécution VOS POSIX comble cette différence en mettant en mémoire tampon l'enregistrement en cours dans l'espace utilisateur, en effectuant les opérations d'E/S POSIX sur cette mémoire tampon, puis en réécrivant l'enregistrement mis en mémoire tampon aux moments opportuns.

Si le programme POSIX connaît la taille de chaque enregistrement (par exemple, dans le cas d'un fichier fixe) et s'il lit et écrit exactement le nombre d'octets requis, la présence du tampon n'a alors aucune incidence sur l'opération, et la correspondance entre les deux types d'opérations d'E/S est facile à comprendre et efficace.

Mais si le programme POSIX se contente de lire ou d'écrire un flux d'octets sans tenir compte de la taille des enregistrements sous-jacents, alors la mise en correspondance entre la sémantique POSIX et la sémantique VOS, bien que clairement définie, n'est généralement pas très utile et s'avère souvent assez inefficace. Certaines opérations, telles que la recherche d'une position d'octet ou la réécriture d'une séquence d'octets s'étendant au-delà d'une limite d'enregistrement, sont au mieux inefficaces et au pire impossibles.

Il y a ensuite la question du traitement des caractères de nouvelle ligne.

Les fichiers réguliers POSIX et les fichiers de flux VOS utilisent tous deux le caractère de nouvelle ligne pour marquer la fin d'un enregistrement. Cependant, les enregistrements VOS dans les fichiers structurés ne contiennent généralement pas de caractères de nouvelle ligne. Par exemple, lorsqu'un éditeur VOS (tel que edit, emacs ou line_edit) crée un nouveau fichier séquentiel, chaque enregistrement contient une ligne de texte. Mais l'enregistrement ne se termine pas par un caractère de nouvelle ligne. Par convention, tous les programmes partent du principe qu'un fichier séquentiel contenant du texte comporte un saut de ligne implicite à la fin de chaque enregistrement. Il en va de même pour les fichiers relatifs et fixes. Mais voici un point important : aucun attribut d'un fichier (VOS, Unix, structuré ou non structuré) n'indique si le fichier contient du texte ou des données binaires. Cette distinction est laissée à l'appréciation des programmes qui accèdent au fichier.

Cette situation pose un véritable casse-tête au moteur d'exécution POSIX de VOS. Il doit déterminer si un fichier structuré VOS contient du texte ou des données afin de savoir s'il doit ajouter un saut de ligne à la fin de chaque enregistrement ou non. Si le fichier contient du texte, il doit ajouter un saut de ligne. S'il contient des données, il ne doit pas ajouter de saut de ligne.

La réponse est que le runtime POSIX de VOS s'en remet à l'appelant pour fournir cette information. Par défaut, le runtime POSIX traite les fichiers structurés comme s'ils contenaient du texte et ajoute un caractère de fin de ligne ; un appelant peut demander explicitement ce comportement en spécifiant le mode d'ouverture O_TEXT. Un appelant qui souhaite traiter un fichier structuré VOS comme contenant des données doit fournir le mode d'ouverture O_BINARY. Ces deux modes s'excluent mutuellement ; si vous spécifiez l'un d'entre eux, vous ne devez pas spécifier l'autre. Ces modes ne sont pas nécessaires pour les fichiers de flux et sont donc ignorés dans ce cas.

À l'intention des juristes spécialisés en informatique qui lisent cet article, je tiens à préciser rapidement que O_TEXT et O_BINARY sont toutes deux des extensions de la norme POSIX ; elles ne sont pas définies par POSIX elle-même. Elles ne sont généralement présentes que sur les systèmes d'exploitation qui font la distinction entre les fichiers texte et les fichiers binaires (comme VOS), ou qui utilisent une convention particulière pour la fin de ligne (comme Windows, qui utilise CR-LF).

Conformément à notre politique, lorsque Stratus des logiciels basés sur POSIX vers OpenVOS, nous les modifions afin d'exclure l'utilisation de fichiers FIXED et RELATIVE, et nous limitons les fichiers SEQUENTIAL à un accès en lecture seule. Nous partons également du principe que tous les fichiers séquentiels contiennent du texte. D'après notre expérience, ces règles permettent d'utiliser de manière pratique des fichiers STREAM ou SEQUENTIAL comme entrée pour les programmes POSIX, tout en évitant les inefficacités inhérentes à la tentative d'effectuer des opérations orientées octet sur des fichiers de sortie SEQUENTIAL.

En résumé, la meilleure approche consiste à n'utiliser que des fichiers STREAM (pour l'entrée ou la sortie) et des fichiers SEQUENTIAL (pour l'entrée de texte uniquement) avec les programmes basés sur POSIX. Si vous disposez de données binaires dans un fichier structuré, écrivez un petit programme pour les copier dans un fichier STREAM, puis utilisez la version STREAM du fichier avec les programmes POSIX. Si vous disposez de données textuelles dans un fichier FIXED ou RELATIVE que vous souhaitez traiter avec des programmes POSIX, copiez d'abord le fichier dans un fichier STREAM.