Forum Graph100

Forum Graph100

Vous n'êtes pas identifié.

Annonce

Bonjour et bienvenue sur le nouveau Forum Graph100 !
L'intégralité des données a été transférée sur un forum PunBB et tout les comptes sont fonctionnels avec le même nom d'utilisateur et mot de passe.
Un wiki est aussi disponible avec le même compte ! N'oubliez pas de remettre votre avatar, bon surf !
Pour plus d'informations, consultez ce post.

#1 15 Nov 2003 17:51:43

Swifter
Programmeur Graph100
Lieu: Niort (79)
Date d'inscription: 06 Aug 2002
Messages: 980
Site web

Pointeur Far

Voila, j'ai un bug à Chess, qui m'embête depuis un bout de temps...
Une fonction censée afficher une chaîne de caractères marche correctement, jusqu'à ce qu'à un certain moment (après répétition de la même action un certain nombre de fois), le contenu de la chaîne stocké dans la mémoire de la caltos change (un caractère est changé : par exemple le caractère E passe à F...).
Donc si certain connaissent l'origine de ce bug, merci de me le signaler...
Mais je voudrais aussi savoir une information qui pourrait me permettre de résoudre ce bug (enfin, plutôt le contourner). Prenons l'exemple suivant :

Code:

void print(unsigned char far* string)
{
  asm lds si,string
  ......
}

print("Bug de merde");

Imaginons que la chaine "Bug de merde" est stockée à l'adresse 0x8463:FFE2.
Tandis que le pointeur string est déclaré à l'adresse 0x82A0:56B1.
Voila j'ai l'habitude de récupérer l'adresse du pointeur grâce à la commande assembleur lds mais en fait je voudrais récupérer celle de "Bug de merde"...
Voila...


Swifter, avec un T, n'attrapes pas la poussière mais toutes les remarques débiles :mrgreen:
              ** Swifter68@hotmail.com **

Hors ligne

 

#2 15 Nov 2003 19:05:48

2072
Programmeur Graph100
Lieu: Somewherebourg
Date d'inscription: 29 Jan 2002
Messages: 2056
Site web

Re: Pointeur Far

laisse tombé, un "pointeur" far est en fait un unsigned long de 4 octets... tu ne peux pas le récupéré en asm de cette façon là... C'est une invention de Borland les far, et il n'y a que TC qui les gère.

les 2 octets de poids forts correspondent au segment et ceux de poid faible à l'offset. En fait ton bug viens du fait que tu écris n'importe où dans la mémoire lol

Regarde dans les sources de memzone pour voir comment je deal avec les far en asm ;-)

récupérer l'adresse du pointeur

ça n'est pas plutôt l'adresse vers laquelle le pointeur pointe que tu veux récupéré ?

je ne sais pas ce que fait l'instruction "lds", mais ta chaîne ne peux pas être un pointeur far puisque on compile en tiny, ton code devrais être:

Code:

void print(unsigned char * string) 
{
int adressedelachaineparrapportaDS;

 adressedelachaineparrapportaDS= (int)string;
} 

print("Bug de merde"); 

-~2072~-
Paid Emails
[URL=http://www.2072productions.com]2072productions.com[/URL]
[URL=http://www.casiocalc.org]casiocalc.org[/URL]

Hors ligne

 

#3 16 Nov 2003 04:23:44

Julien
C++iste convaincu
Lieu: Waterloo (Be)
Date d'inscription: 29 May 2002
Messages: 1456
Site web

Re: Pointeur Far

laisse tombé, un "pointeur" far est en fait un unsigned long de 4 octets... tu ne peux pas le récupéré en asm de cette façon là... C'est une invention de Borland les far, et il n'y a que TC qui les gère.

Sonic est bourré de pointeurs far que je gere en asm avec "lds" et "les", exactement comme Swifter (en plus je pense qu'il bosse aussi en cpp), et je n'ai aucun bug! (bon d'accord ca m'a pris une semaine pour que ca soit au point, mais maintenant c OK  big_smile )

En fait je fais la meme chose pour ma fonction d'affichage de sprites, qui est déclarée comme ca:
void drawsprite(int x,char y,void far* spr);

La plupart du temps je lui donne un pointeur far directement vers le contenu de la memzone où sont stockés tous les sprites l'un derrière l'autre, mais parfois j'ai aussi des sprites déclarés dans le prog lui-meme, par exemple
u_char UnSprite[]={ ... };
et je peux faire drawsprite( ... , ... , UnSprite); sans le moindre problème  smile

Petite note qd meme sur lds, parce qu'apparemment c pas clair:

Si je fais un pointeur far, disons
unisigned char far* ptr=(unsigned char far*)MK_FP(0x8463,0xFFE2);
il indique donc bien l'offset 0xFFE2 dans le segment 0x8463.

Si en asm je fais
lds si,ptr
alors ca revient bien à mettre le numero du segment (0x8463) dans ds et le numero de l'offset (0xFFE2) dans si.
Donc après ca faire en asm
mov al,[si]
c la meme chose que faire en cpp _AL=*ptr; (sauf qu'il faudra faire gaffe parce qu'on a modifié ds en asm)

On peut aussi faire
les ax,ptr
par exemple, ca ca mettra le segment dans es et l'offset dans ax.

donc lds et les c bien pour charger l'adresse indiquée par le pointeur, pas l'adresse du pointeur lui-meme wink

Sinon allez jeter un oeil aux sources de sonic, ca peut servir  wink


Pensez à surveiller mes releases wink

Hors ligne

 

#4 16 Nov 2003 05:10:49

Swifter
Programmeur Graph100
Lieu: Niort (79)
Date d'inscription: 06 Aug 2002
Messages: 980
Site web

Re: Pointeur Far

bin en fait j'ai été obligé de passer au pointeur far...
C'était l'origine de pas mal de bug dans Chess...
En fait une routine classique memcopy qui copie les donnees d'une adresse à une autre faisait écrire des données n'importe où dans la mémoire.

Code:

void memcopy(unsigned char* adr_src,unsigned char adr_dest,unsigned int size)
{
   asm mov si,adr_src
   .........
}

unsigned char* new_str="test";  // adresse de new_str 0x802F:0x25A3
   
if (condition_quelconque)
{
   unsigned char* string="123456789"; // adresse de string 0x8486:0xFFE2
   memcopy(new_str,string,5);
}

Et c'est la que ca plantait puisque ca copiait de l'adresse 0x802F:0x25A3 à 0x802F:0xFFE2 au lieu de 0x802F:0x25A3 à 0x8486:0xFFE2.

Donc voila juste pour dire que je n'écris pas n'importe où dans la mémoire puisque l'insertion des pointeurs far avait pour but de résoudre ce bug.

Sinon je ne veux pas récuperer l'adresse du pointeur puisque je l'obtient avec lds...
Pour ds modifié un push et pop suffisent pour régler ce probleme...

En fait pour mieux expliquer le premier exemple : un octet de l'adresse 0x8463:FFE2 est modifié une bonne fois pour toute alors que je n ele souhaite pas...


Swifter, avec un T, n'attrapes pas la poussière mais toutes les remarques débiles :mrgreen:
              ** Swifter68@hotmail.com **

Hors ligne

 

#5 16 Nov 2003 05:22:59

Julien
C++iste convaincu
Lieu: Waterloo (Be)
Date d'inscription: 29 May 2002
Messages: 1456
Site web

Re: Pointeur Far

Ah ben oui si les segments de la source et de la destination sont pas les memes, il faut passer aux far...

Moi je fais

Code:

void copy(void far* src, void far* dest, u_int taille)
{    //deplace 'taille' octets de l'emplacement 'src' vers 'dest'
asm {
    push ds
    cld

    mov cx, taille
    les di,dest            // es = segment du pointeur dest, di = offset
    lds si,src            // ds = segment du pointeur src, si = offset

    shr cx,1            // nombre de mots a copier
    jnc move_suite

    movsb                // si le nombre d'octets a copier est impair
    
} move_suite: asm {

    rep movsw            // copie chaque mot

    pop ds
    }
}

Et puis

Code:

unsigned char* new_str="test";  // adresse de new_str 0x802F:0x25A3 
    
if (condition_quelconque) 
{ 
   unsigned char* string="123456789"; // adresse de string 0x8486:0xFFE2 
   copy(new_str,string,5); 
} 

Et c ok...


Pensez à surveiller mes releases wink

Hors ligne

 

#6 16 Nov 2003 17:37:32

2072
Programmeur Graph100
Lieu: Somewherebourg
Date d'inscription: 29 Jan 2002
Messages: 2056
Site web

Re: Pointeur Far

Ah ok, je ne conaissait pas lds. Donc ça récupère bien l'adresse indiqué par un pointeur far.




Ah ben oui si les segments de la source et de la destination sont pas les memes, il faut passer aux far...

Non en fait c'est si les segments de la source et de la destination ne sont pas DS. Un pointeur en C est un unsigned int qui ne contient que l'offset par rapport à DS. Donc si ton pointeur n'est pas un far il ne contiendra que l'offset par rapport à DS

Essaye de faire des pop et push avec tous les registres que tu utilises ainsi qu'un pushf popf au moins tu est sûr de ce qu'il se passe. Car je ne sais pas si TC le fait lui même, à priori on pourrais croire que non puisque DS n'est pas restoré autaumatiquement...


-~2072~-
Paid Emails
[URL=http://www.2072productions.com]2072productions.com[/URL]
[URL=http://www.casiocalc.org]casiocalc.org[/URL]

Hors ligne

 

#7 17 Nov 2003 08:05:01

Julien
C++iste convaincu
Lieu: Waterloo (Be)
Date d'inscription: 29 May 2002
Messages: 1456
Site web

Re: Pointeur Far

Moui pour ce qui est de la sauvegarde des registres, en fait on s'en fiche, le seul qui est important c'est effectivement ds... TCC ne va jamais utiliser un registre autre que ds qui aurait pu etre modifié involontairement; il suffit d'examiner les traductions asm générées pour voir comment ca se passe big_smile


Pensez à surveiller mes releases wink

Hors ligne

 

#8 17 Nov 2003 19:38:53

2072
Programmeur Graph100
Lieu: Somewherebourg
Date d'inscription: 29 Jan 2002
Messages: 2056
Site web

Re: Pointeur Far

il n'utilise pas de registre  :?: tu pourrais me montre un exemple de code asm généré par TCC (j'ai une grosse flémite en ce moment).

merci


-~2072~-
Paid Emails
[URL=http://www.2072productions.com]2072productions.com[/URL]
[URL=http://www.casiocalc.org]casiocalc.org[/URL]

Hors ligne

 

#9 18 Nov 2003 12:34:46

Julien
C++iste convaincu
Lieu: Waterloo (Be)
Date d'inscription: 29 May 2002
Messages: 1456
Site web

Re: Pointeur Far

TC utilise les registres bien entendu, mais seulement qd c lui qui en a "fixé" la valeur; il n'utilisera jamais AX ou ES (ou les autres, sauf DS) si une fonction vient d'etre appelée ou si du code asm inline a été inséré, donc si sa valeur n'est pas connue a priori... ce qui me parait assez logique en fait  :?
Donc en conclusion, sauvegarder les registres que l'on utilise en asm inline dans un code cpp ne sert qu'à perdre du temps!  lol (sauf pour DS, mais c le seul qui en vaille la peine)
(au fait SI est le seul registre (avec BP) à être sauvegardé automatiquement qd il est utilisé par TC... Les autres étant des "registres de travail", leur modification ne devrait pas avoir de conséquences sur la suite si la structure du programme est "correcte".)


Pensez à surveiller mes releases wink

Hors ligne

 

Pied de page des forums

Propulsé par PunBB
© Copyright 2002–2005 Rickard Andersson
Traduction par punbb.fr