imports.h revision 10067e464132e6d484c34dd277da5eb5e21cf491
1/* 2 * Mesa 3-D graphics library 3 * Version: 7.5 4 * 5 * Copyright (C) 1999-2008 Brian Paul All Rights Reserved. 6 * 7 * Permission is hereby granted, free of charge, to any person obtaining a 8 * copy of this software and associated documentation files (the "Software"), 9 * to deal in the Software without restriction, including without limitation 10 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 11 * and/or sell copies of the Software, and to permit persons to whom the 12 * Software is furnished to do so, subject to the following conditions: 13 * 14 * The above copyright notice and this permission notice shall be included 15 * in all copies or substantial portions of the Software. 16 * 17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 18 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 19 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 20 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 21 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 */ 24 25 26/** 27 * \file imports.h 28 * Standard C library function wrappers. 29 * 30 * This file provides wrappers for all the standard C library functions 31 * like malloc(), free(), printf(), getenv(), etc. 32 */ 33 34 35#ifndef IMPORTS_H 36#define IMPORTS_H 37 38 39#include "compiler.h" 40#include "glheader.h" 41 42 43#ifdef __cplusplus 44extern "C" { 45#endif 46 47 48/**********************************************************************/ 49/** Memory macros */ 50/*@{*/ 51 52/** Allocate \p BYTES bytes */ 53#define MALLOC(BYTES) _mesa_malloc(BYTES) 54/** Allocate and zero \p BYTES bytes */ 55#define CALLOC(BYTES) _mesa_calloc(BYTES) 56/** Allocate a structure of type \p T */ 57#define MALLOC_STRUCT(T) (struct T *) _mesa_malloc(sizeof(struct T)) 58/** Allocate and zero a structure of type \p T */ 59#define CALLOC_STRUCT(T) (struct T *) _mesa_calloc(sizeof(struct T)) 60/** Free memory */ 61#define FREE(PTR) _mesa_free(PTR) 62 63/** Allocate \p BYTES aligned at \p N bytes */ 64#define ALIGN_MALLOC(BYTES, N) _mesa_align_malloc(BYTES, N) 65/** Allocate and zero \p BYTES bytes aligned at \p N bytes */ 66#define ALIGN_CALLOC(BYTES, N) _mesa_align_calloc(BYTES, N) 67/** Allocate a structure of type \p T aligned at \p N bytes */ 68#define ALIGN_MALLOC_STRUCT(T, N) (struct T *) _mesa_align_malloc(sizeof(struct T), N) 69/** Allocate and zero a structure of type \p T aligned at \p N bytes */ 70#define ALIGN_CALLOC_STRUCT(T, N) (struct T *) _mesa_align_calloc(sizeof(struct T), N) 71/** Free aligned memory */ 72#define ALIGN_FREE(PTR) _mesa_align_free(PTR) 73 74/** Copy \p BYTES bytes from \p SRC into \p DST */ 75#define MEMCPY( DST, SRC, BYTES) _mesa_memcpy(DST, SRC, BYTES) 76/** Set \p N bytes in \p DST to \p VAL */ 77#define MEMSET( DST, VAL, N ) _mesa_memset(DST, VAL, N) 78 79/*@}*/ 80 81 82/* 83 * For GL_ARB_vertex_buffer_object we need to treat vertex array pointers 84 * as offsets into buffer stores. Since the vertex array pointer and 85 * buffer store pointer are both pointers and we need to add them, we use 86 * this macro. 87 * Both pointers/offsets are expressed in bytes. 88 */ 89#define ADD_POINTERS(A, B) ( (GLubyte *) (A) + (uintptr_t) (B) ) 90 91 92/** 93 * Sometimes we treat GLfloats as GLints. On x86 systems, moving a float 94 * as a int (thereby using integer registers instead of FP registers) is 95 * a performance win. Typically, this can be done with ordinary casts. 96 * But with gcc's -fstrict-aliasing flag (which defaults to on in gcc 3.0) 97 * these casts generate warnings. 98 * The following union typedef is used to solve that. 99 */ 100typedef union { GLfloat f; GLint i; } fi_type; 101 102 103 104/********************************************************************** 105 * Math macros 106 */ 107 108#define MAX_GLUSHORT 0xffff 109#define MAX_GLUINT 0xffffffff 110 111/* Degrees to radians conversion: */ 112#define DEG2RAD (M_PI/180.0) 113 114 115/*** 116 *** SQRTF: single-precision square root 117 ***/ 118#if 0 /* _mesa_sqrtf() not accurate enough - temporarily disabled */ 119# define SQRTF(X) _mesa_sqrtf(X) 120#else 121# define SQRTF(X) (float) sqrt((float) (X)) 122#endif 123 124 125/*** 126 *** INV_SQRTF: single-precision inverse square root 127 ***/ 128#if 0 129#define INV_SQRTF(X) _mesa_inv_sqrt(X) 130#else 131#define INV_SQRTF(X) (1.0F / SQRTF(X)) /* this is faster on a P4 */ 132#endif 133 134 135/*** 136 *** LOG2: Log base 2 of float 137 ***/ 138#ifdef USE_IEEE 139#if 0 140/* This is pretty fast, but not accurate enough (only 2 fractional bits). 141 * Based on code from http://www.stereopsis.com/log2.html 142 */ 143static INLINE GLfloat LOG2(GLfloat x) 144{ 145 const GLfloat y = x * x * x * x; 146 const GLuint ix = *((GLuint *) &y); 147 const GLuint exp = (ix >> 23) & 0xFF; 148 const GLint log2 = ((GLint) exp) - 127; 149 return (GLfloat) log2 * (1.0 / 4.0); /* 4, because of x^4 above */ 150} 151#endif 152/* Pretty fast, and accurate. 153 * Based on code from http://www.flipcode.com/totd/ 154 */ 155static INLINE GLfloat LOG2(GLfloat val) 156{ 157 fi_type num; 158 GLint log_2; 159 num.f = val; 160 log_2 = ((num.i >> 23) & 255) - 128; 161 num.i &= ~(255 << 23); 162 num.i += 127 << 23; 163 num.f = ((-1.0f/3) * num.f + 2) * num.f - 2.0f/3; 164 return num.f + log_2; 165} 166#else 167/* 168 * NOTE: log_base_2(x) = log(x) / log(2) 169 * NOTE: 1.442695 = 1/log(2). 170 */ 171#define LOG2(x) ((GLfloat) (log(x) * 1.442695F)) 172#endif 173 174 175/*** 176 *** IS_INF_OR_NAN: test if float is infinite or NaN 177 ***/ 178#ifdef USE_IEEE 179static INLINE int IS_INF_OR_NAN( float x ) 180{ 181 fi_type tmp; 182 tmp.f = x; 183 return !(int)((unsigned int)((tmp.i & 0x7fffffff)-0x7f800000) >> 31); 184} 185#elif defined(isfinite) 186#define IS_INF_OR_NAN(x) (!isfinite(x)) 187#elif defined(finite) 188#define IS_INF_OR_NAN(x) (!finite(x)) 189#elif defined(__VMS) 190#define IS_INF_OR_NAN(x) (!finite(x)) 191#elif defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L 192#define IS_INF_OR_NAN(x) (!isfinite(x)) 193#else 194#define IS_INF_OR_NAN(x) (!finite(x)) 195#endif 196 197 198/*** 199 *** IS_NEGATIVE: test if float is negative 200 ***/ 201#if defined(USE_IEEE) 202static INLINE int GET_FLOAT_BITS( float x ) 203{ 204 fi_type fi; 205 fi.f = x; 206 return fi.i; 207} 208#define IS_NEGATIVE(x) (GET_FLOAT_BITS(x) < 0) 209#else 210#define IS_NEGATIVE(x) (x < 0.0F) 211#endif 212 213 214/*** 215 *** DIFFERENT_SIGNS: test if two floats have opposite signs 216 ***/ 217#if defined(USE_IEEE) 218#define DIFFERENT_SIGNS(x,y) ((GET_FLOAT_BITS(x) ^ GET_FLOAT_BITS(y)) & (1<<31)) 219#else 220/* Could just use (x*y<0) except for the flatshading requirements. 221 * Maybe there's a better way? 222 */ 223#define DIFFERENT_SIGNS(x,y) ((x) * (y) <= 0.0F && (x) - (y) != 0.0F) 224#endif 225 226 227/*** 228 *** CEILF: ceiling of float 229 *** FLOORF: floor of float 230 *** FABSF: absolute value of float 231 *** LOGF: the natural logarithm (base e) of the value 232 *** EXPF: raise e to the value 233 *** LDEXPF: multiply value by an integral power of two 234 *** FREXPF: extract mantissa and exponent from value 235 ***/ 236#if defined(__gnu_linux__) 237/* C99 functions */ 238#define CEILF(x) ceilf(x) 239#define FLOORF(x) floorf(x) 240#define FABSF(x) fabsf(x) 241#define LOGF(x) logf(x) 242#define EXPF(x) expf(x) 243#define LDEXPF(x,y) ldexpf(x,y) 244#define FREXPF(x,y) frexpf(x,y) 245#else 246#define CEILF(x) ((GLfloat) ceil(x)) 247#define FLOORF(x) ((GLfloat) floor(x)) 248#define FABSF(x) ((GLfloat) fabs(x)) 249#define LOGF(x) ((GLfloat) log(x)) 250#define EXPF(x) ((GLfloat) exp(x)) 251#define LDEXPF(x,y) ((GLfloat) ldexp(x,y)) 252#define FREXPF(x,y) ((GLfloat) frexp(x,y)) 253#endif 254 255 256/*** 257 *** IROUND: return (as an integer) float rounded to nearest integer 258 ***/ 259#if defined(USE_X86_ASM) && defined(__GNUC__) && defined(__i386__) && \ 260 (!(defined(__BEOS__) || defined(__HAIKU__)) || \ 261 (__GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95))) 262static INLINE int iround(float f) 263{ 264 int r; 265 __asm__ ("fistpl %0" : "=m" (r) : "t" (f) : "st"); 266 return r; 267} 268#define IROUND(x) iround(x) 269#elif defined(USE_X86_ASM) && defined(_MSC_VER) 270static INLINE int iround(float f) 271{ 272 int r; 273 _asm { 274 fld f 275 fistp r 276 } 277 return r; 278} 279#define IROUND(x) iround(x) 280#elif defined(__WATCOMC__) && defined(__386__) 281long iround(float f); 282#pragma aux iround = \ 283 "push eax" \ 284 "fistp dword ptr [esp]" \ 285 "pop eax" \ 286 parm [8087] \ 287 value [eax] \ 288 modify exact [eax]; 289#define IROUND(x) iround(x) 290#else 291#define IROUND(f) ((int) (((f) >= 0.0F) ? ((f) + 0.5F) : ((f) - 0.5F))) 292#endif 293 294#define IROUND64(f) ((GLint64) (((f) >= 0.0F) ? ((f) + 0.5F) : ((f) - 0.5F))) 295 296/*** 297 *** IROUND_POS: return (as an integer) positive float rounded to nearest int 298 ***/ 299#ifdef DEBUG 300#define IROUND_POS(f) (assert((f) >= 0.0F), IROUND(f)) 301#else 302#define IROUND_POS(f) (IROUND(f)) 303#endif 304 305 306/*** 307 *** IFLOOR: return (as an integer) floor of float 308 ***/ 309#if defined(USE_X86_ASM) && defined(__GNUC__) && defined(__i386__) 310/* 311 * IEEE floor for computers that round to nearest or even. 312 * 'f' must be between -4194304 and 4194303. 313 * This floor operation is done by "(iround(f + .5) + iround(f - .5)) >> 1", 314 * but uses some IEEE specific tricks for better speed. 315 * Contributed by Josh Vanderhoof 316 */ 317static INLINE int ifloor(float f) 318{ 319 int ai, bi; 320 double af, bf; 321 af = (3 << 22) + 0.5 + (double)f; 322 bf = (3 << 22) + 0.5 - (double)f; 323 /* GCC generates an extra fstp/fld without this. */ 324 __asm__ ("fstps %0" : "=m" (ai) : "t" (af) : "st"); 325 __asm__ ("fstps %0" : "=m" (bi) : "t" (bf) : "st"); 326 return (ai - bi) >> 1; 327} 328#define IFLOOR(x) ifloor(x) 329#elif defined(USE_IEEE) 330static INLINE int ifloor(float f) 331{ 332 int ai, bi; 333 double af, bf; 334 fi_type u; 335 336 af = (3 << 22) + 0.5 + (double)f; 337 bf = (3 << 22) + 0.5 - (double)f; 338 u.f = (float) af; ai = u.i; 339 u.f = (float) bf; bi = u.i; 340 return (ai - bi) >> 1; 341} 342#define IFLOOR(x) ifloor(x) 343#else 344static INLINE int ifloor(float f) 345{ 346 int i = IROUND(f); 347 return (i > f) ? i - 1 : i; 348} 349#define IFLOOR(x) ifloor(x) 350#endif 351 352 353/*** 354 *** ICEIL: return (as an integer) ceiling of float 355 ***/ 356#if defined(USE_X86_ASM) && defined(__GNUC__) && defined(__i386__) 357/* 358 * IEEE ceil for computers that round to nearest or even. 359 * 'f' must be between -4194304 and 4194303. 360 * This ceil operation is done by "(iround(f + .5) + iround(f - .5) + 1) >> 1", 361 * but uses some IEEE specific tricks for better speed. 362 * Contributed by Josh Vanderhoof 363 */ 364static INLINE int iceil(float f) 365{ 366 int ai, bi; 367 double af, bf; 368 af = (3 << 22) + 0.5 + (double)f; 369 bf = (3 << 22) + 0.5 - (double)f; 370 /* GCC generates an extra fstp/fld without this. */ 371 __asm__ ("fstps %0" : "=m" (ai) : "t" (af) : "st"); 372 __asm__ ("fstps %0" : "=m" (bi) : "t" (bf) : "st"); 373 return (ai - bi + 1) >> 1; 374} 375#define ICEIL(x) iceil(x) 376#elif defined(USE_IEEE) 377static INLINE int iceil(float f) 378{ 379 int ai, bi; 380 double af, bf; 381 fi_type u; 382 af = (3 << 22) + 0.5 + (double)f; 383 bf = (3 << 22) + 0.5 - (double)f; 384 u.f = (float) af; ai = u.i; 385 u.f = (float) bf; bi = u.i; 386 return (ai - bi + 1) >> 1; 387} 388#define ICEIL(x) iceil(x) 389#else 390static INLINE int iceil(float f) 391{ 392 int i = IROUND(f); 393 return (i < f) ? i + 1 : i; 394} 395#define ICEIL(x) iceil(x) 396#endif 397 398 399/** 400 * Is x a power of two? 401 */ 402static INLINE int 403_mesa_is_pow_two(int x) 404{ 405 return !(x & (x - 1)); 406} 407 408 409/*** 410 *** UNCLAMPED_FLOAT_TO_UBYTE: clamp float to [0,1] and map to ubyte in [0,255] 411 *** CLAMPED_FLOAT_TO_UBYTE: map float known to be in [0,1] to ubyte in [0,255] 412 ***/ 413#if defined(USE_IEEE) && !defined(DEBUG) 414#define IEEE_0996 0x3f7f0000 /* 0.996 or so */ 415/* This function/macro is sensitive to precision. Test very carefully 416 * if you change it! 417 */ 418#define UNCLAMPED_FLOAT_TO_UBYTE(UB, F) \ 419 do { \ 420 fi_type __tmp; \ 421 __tmp.f = (F); \ 422 if (__tmp.i < 0) \ 423 UB = (GLubyte) 0; \ 424 else if (__tmp.i >= IEEE_0996) \ 425 UB = (GLubyte) 255; \ 426 else { \ 427 __tmp.f = __tmp.f * (255.0F/256.0F) + 32768.0F; \ 428 UB = (GLubyte) __tmp.i; \ 429 } \ 430 } while (0) 431#define CLAMPED_FLOAT_TO_UBYTE(UB, F) \ 432 do { \ 433 fi_type __tmp; \ 434 __tmp.f = (F) * (255.0F/256.0F) + 32768.0F; \ 435 UB = (GLubyte) __tmp.i; \ 436 } while (0) 437#else 438#define UNCLAMPED_FLOAT_TO_UBYTE(ub, f) \ 439 ub = ((GLubyte) IROUND(CLAMP((f), 0.0F, 1.0F) * 255.0F)) 440#define CLAMPED_FLOAT_TO_UBYTE(ub, f) \ 441 ub = ((GLubyte) IROUND((f) * 255.0F)) 442#endif 443 444 445/** 446 * Return 1 if this is a little endian machine, 0 if big endian. 447 */ 448static INLINE GLboolean 449_mesa_little_endian(void) 450{ 451 const GLuint ui = 1; /* intentionally not static */ 452 return *((const GLubyte *) &ui); 453} 454 455 456 457/********************************************************************** 458 * Functions 459 */ 460 461extern void * 462_mesa_malloc( size_t bytes ); 463 464extern void * 465_mesa_calloc( size_t bytes ); 466 467extern void 468_mesa_free( void *ptr ); 469 470extern void * 471_mesa_align_malloc( size_t bytes, unsigned long alignment ); 472 473extern void * 474_mesa_align_calloc( size_t bytes, unsigned long alignment ); 475 476extern void 477_mesa_align_free( void *ptr ); 478 479extern void * 480_mesa_align_realloc(void *oldBuffer, size_t oldSize, size_t newSize, 481 unsigned long alignment); 482 483extern void * 484_mesa_exec_malloc( GLuint size ); 485 486extern void 487_mesa_exec_free( void *addr ); 488 489extern void * 490_mesa_realloc( void *oldBuffer, size_t oldSize, size_t newSize ); 491 492extern void * 493_mesa_memcpy( void *dest, const void *src, size_t n ); 494 495extern void 496_mesa_memset( void *dst, int val, size_t n ); 497 498extern void 499_mesa_memset16( unsigned short *dst, unsigned short val, size_t n ); 500 501extern void 502_mesa_bzero( void *dst, size_t n ); 503 504extern int 505_mesa_memcmp( const void *s1, const void *s2, size_t n ); 506 507extern double 508_mesa_sin(double a); 509 510extern float 511_mesa_sinf(float a); 512 513extern double 514_mesa_cos(double a); 515 516extern float 517_mesa_asinf(float x); 518 519extern float 520_mesa_atanf(float x); 521 522extern double 523_mesa_sqrtd(double x); 524 525extern float 526_mesa_sqrtf(float x); 527 528extern float 529_mesa_inv_sqrtf(float x); 530 531extern void 532_mesa_init_sqrt_table(void); 533 534extern double 535_mesa_pow(double x, double y); 536 537extern int 538_mesa_ffs(int32_t i); 539 540extern int 541_mesa_ffsll(int64_t i); 542 543extern unsigned int 544_mesa_bitcount(unsigned int n); 545 546extern GLhalfARB 547_mesa_float_to_half(float f); 548 549extern float 550_mesa_half_to_float(GLhalfARB h); 551 552 553extern void * 554_mesa_bsearch( const void *key, const void *base, size_t nmemb, size_t size, 555 int (*compar)(const void *, const void *) ); 556 557extern char * 558_mesa_getenv( const char *var ); 559 560extern char * 561_mesa_strstr( const char *haystack, const char *needle ); 562 563extern char * 564_mesa_strncat( char *dest, const char *src, size_t n ); 565 566extern char * 567_mesa_strcpy( char *dest, const char *src ); 568 569extern char * 570_mesa_strncpy( char *dest, const char *src, size_t n ); 571 572extern size_t 573_mesa_strlen( const char *s ); 574 575extern int 576_mesa_strcmp( const char *s1, const char *s2 ); 577 578extern int 579_mesa_strncmp( const char *s1, const char *s2, size_t n ); 580 581extern char * 582_mesa_strdup( const char *s ); 583 584extern int 585_mesa_atoi( const char *s ); 586 587extern double 588_mesa_strtod( const char *s, char **end ); 589 590extern unsigned int 591_mesa_str_checksum(const char *str); 592 593extern int 594_mesa_sprintf( char *str, const char *fmt, ... ); 595 596extern int 597_mesa_snprintf( char *str, size_t size, const char *fmt, ... ); 598 599extern void 600_mesa_printf( const char *fmtString, ... ); 601 602extern void 603_mesa_fprintf( FILE *f, const char *fmtString, ... ); 604 605extern int 606_mesa_vsprintf( char *str, const char *fmt, va_list args ); 607 608 609extern void 610_mesa_warning( __GLcontext *gc, const char *fmtString, ... ); 611 612extern void 613_mesa_problem( const __GLcontext *ctx, const char *fmtString, ... ); 614 615extern void 616_mesa_error( __GLcontext *ctx, GLenum error, const char *fmtString, ... ); 617 618extern void 619_mesa_debug( const __GLcontext *ctx, const char *fmtString, ... ); 620 621extern void 622_mesa_exit( int status ); 623 624 625#ifdef __cplusplus 626} 627#endif 628 629 630#endif /* IMPORTS_H */ 631