delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp/1994/10/11/16:56:03

Date: Tue, 11 Oct 1994 11:28:27 -0400 (EDT)
From: Kimberley Burchett <OKRA AT max DOT tiac DOT net>
Subject: keyboard messups from hell
To: DJGPP Mailing List <djgpp AT sun DOT soe DOT clarkson DOT edu>

  My old version of FixRotate() was declared inline.  I took that out and
the problem is gone.  ARGH!!!!  I'm going to post all the code FixRotate
uses right here.  I'd post all the code necessary to compile the test 
program, but it's like 11 pages since most of the functions in the graph 
lib are built upon earlier functions.  Besides, it's intel/VGA dependant.
  FixRotate() uses an inline assembly function in fixed.h - FixMul.
  The other example I quoted that required a rearranging of the while 
construct didn't use any inline assembler.  However, both of the 
functions inside the while loop where declared inline.   BUT - even 
though they were declared inline, they really weren't since I include the 
graphics lib only at the linking stage.  Complicated, no? :)
  In case you're wondering, in the inline assembler, the registers that 
are messed up ARE clearly marked as ruined.


-------------------------- fixed.h ---------------------
 
#ifndef _FIXED_H_
#define _FIXED_H_

#include "usefuls.h"  /* included for int_sqrt() function and SQR() macro */
 
typedef long fixed;
 
#define FixBits 16
#define Fix1       65536     /* one in fixed point */
#define FixPI      (Fix1/2)  /* fixed point 1 = full rotation */
 
#define FixMul(x, y)                            \
  ({ fixed result;                              \
     asm("imul %1; shrdl $16,%%edx,%%eax" :     \
         "=a" (result) : "r" (x), "a" (y) :     \
         "%%eax", "%%edx", "cc");               \
     result;})
 
#define FixDiv(x, y)                                            \
  ({ fixed result;                                              \
     asm("cdq; shldl $16,%%eax,%%edx; sall $16,%%eax; idiv %2" :\
         "=a" (result) : "a" (x), "r" (y), "d" (0) :            \
         "%%eax", "%%edx", "cc");                               \
     result;})
 
#define FixWhole(x)  ( (x) >> 16 )
#define FixFrac(x)   ( (x) & 0xFFFF )
#define FixAdd(x,y)  ( (x) + (y) )
#define FixSub(x,y)  ( (x) - (y) )
#define Fix2Int(x)   ( (x) >> 16 )
#define Int2Fix(x)   ( (x) << 16 )
#define Fix2Float(x) ( (x) / 65536.0 )
#define Float2Fix(x) (int)( (x) * 65536 )
#define FixSqrt(x)   (int_sqrt(x) << 8)  /* int_sqrt in usefuls.h */
#define FixDist(x,y) (int_sqrt( SQR( (x) >> 14) + SQR( (y) >> 14) ) << 14)
#define FixMax       (0x7FFFFFFF);
#define FixMin       (-FixMax);
 
 
#endif


-------------------------- 


void FixRotate(fixed x1, fixed y1, fixed angle, fixed *x2, fixed *y2) {
 
  fixed sine, cosine;
 

  /* I substituted so you'd have less code to look at - does the same 
thing, though (same problem shows up with both versions) */

  sine = Float2Fix( sin(PI*angle/(float)FixPI) );
  cosine = Float2Fix( cos(PI*angle/(float)FixPI) );
/*
  sine = FixSin(angle) );    
  cosine = FixCos(angle) );
*/
  *x2 = FixMul(x1,cosine) - FixMul(y1,sine);  /* rotation matrix */
  *y2 = FixMul(y1,cosine) + FixMul(x1,sine);
}


  If anybody feels like poking around with this, go ahead.  If you want 
to use fixed.h go ahead and do that, too.
								Kim

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019