PDA

Archiv verlassen und diese Seite im Standarddesign anzeigen : Krieg ich vielleich ein wenig mehr Speicher?


liquid
2003-02-20, 19:15:52
unsigned long count2 = 100;

while (1)
{
std::cout << "allocating " << count2 << " GLfloat!\n";
GLfloat* array = new GLfloat[count2];
delete [] array;
count2 = count2 + 50;
}


Ausgabe:

allocating 100 GLfloat!
allocating 150 GLfloat!
allocating 200 GLfloat!
allocating 250 GLfloat!
allocating 300 GLfloat!
allocating 350 GLfloat!
allocating 400 GLfloat!
allocating 450 GLfloat!
allocating 500 GLfloat!
allocating 550 GLfloat!
allocating 600 GLfloat!
allocating 650 GLfloat!
allocating 700 GLfloat!
allocating 750 GLfloat!
allocating 800 GLfloat!
allocating 850 GLfloat!
allocating 900 GLfloat!
allocating 950 GLfloat!
allocating 1000 GLfloat!
allocating 1050 GLfloat!


Und dann kommt ein wunderschöner general protection fault. Weiß der Geier warum. Ich hab mal nachgerechnet. Jeder GLfloat hat doch 16 Bit wenn ich mich nicht irre (sind ja keine Doubles). Davon haben wir nach der letzten Ausgabe des Programms genau 1050 Stück, das wären dann 16800 Bit, die zu allokieren wären. Also 2100 Bytes, ein wenig mehr als 2 KB. Was geht denn da ab? Krieg ich vielleicht ein wenig mehr Speicher oder muss ich mit lächerlichen 2KB meinen Terrain Renderer aufbaun?
Hoffentlich haben die Profis ne passende Antwort parat, ich flipp hier nämlich langsam aus. IDE ist Dev-C++ (zeckis Fachgebiet) und Compiler natürlich MinGW-3.2. Kann es vielleicht daran liegen?
Ich hab nämlich erst den Debug Mode ausgehabt und höchste Optimierung bei der Erstellung aktiviert. Dachte eventuell könnte es ja auch daran liegen, wer weiß das schon. Also Debug an und Optimierung aus, aber Pustekuchen immer noch ein dicker general protection fault.
Und RAM Idel zeigt mir 200MB freien Speicher an. Ich wär ja schon droh, wenn ich ganze 2MB kriegen würde, aber mit 2KB kann ich nun wirklich nicht viel anfangen :( *buhuuu*

cya
liquid

Demirug
2003-02-20, 19:39:53
Ein float hat 32 bit ein double 64. Kann man mit sizeof aber ganz leicht herausbekommen.

Bei mir (VC++ 7) läuft das ganze ohne Problem also ist dein Code in Ordnung. DevC++ habe ich nicht hier.

liquid
2003-02-20, 19:59:52
Ok, dann sind es ganze 4KB die ich haben will, auch immer noch ein bischen wenig. Zecki wo bleibst du??
Oder Windows 98SE spinnt einfach ein wenig rum. Arggg...

cya
liquid

zeckensack
2003-02-20, 20:02:47
Bei mir funzt das???

Im Zweifelsfall mal im Tools-Menü von DevCC auf 'Check for Updates/Packages' gehen. Dann DevCC schließen und im neuen Fenster auf's Häkchen klicken, Patches auswählen, nochmal haken, ausharren, weitermachen :)

Die Updates die man so bekommt sind btw nicht in der 'normalen' Distribution enthalten. Könnte also gut sein, daß das ein mittlerweile gefixter Bug ist.

zeckensack
2003-02-20, 20:03:54
Originally posted by liquid
Ok, dann sind es ganze 4KB die ich haben will, auch immer noch ein bischen wenig. Zecki wo bleibst du??
Oder Windows 98SE spinnt einfach ein wenig rum. Arggg...

cya
liquid Juhu! :wink:

Und nochmal neu booten kann auch nicht schaden :D
/win98-flame *eg*

liquid
2003-02-20, 20:23:56
Ich test das mal schön und mach auch noch ein extra Reboot.*g*
Mal sehen wie es weitergeht.

cya
liquid

firewars
2003-02-20, 21:50:51
Funktioniert hier ebenso.

stabilo_boss13
2003-02-20, 22:31:45
Bei mir funktioniert es mit DevC++ (4.9.7.0) und W98 auch.

Versuch doch mal vor dem delete [] mit sizeof(array) herauszufinden, wieviel Speicherplatz wirklich allokiert wurde.

Verwende für count2 nur die Hälfte (also 25) bei jedem Schritt und schaue, ob du jetzt doppelt so viele Schritte machen kannst.

Baue nach dem delete eine Pause ein. Verwende mal std::cin und drücke nach jedem delete eine Taste.

Starte den Rechner neu nach jedem Fehler und prüfe, ob der Fehler jedesmal an der selben Stelle passiert. Starte dazu nach jedem Reboot ein anderes Programm bevor du mit der Fehlersuche beginnst.

Benutze mal float statt GLfloat.

An welcher Stelle im GDB (asm) tritt der Fehler genau auf.

Xmas
2003-02-20, 22:39:48
Originally posted by stabilo_boss13
Versuch doch mal vor dem delete [] mit sizeof(array) herauszufinden, wieviel Speicherplatz wirklich allokiert wurde.
sizeof funktioniert nicht mit dynamisch allokierten Arrays.

stabilo_boss13
2003-02-20, 22:59:06
Originally posted by Xmas

sizeof funktioniert nicht mit dynamisch allokierten Arrays. Stimmt!

Aber ich habe den Fehler glaub ich gefunden:

Muss man da nicht nach dem delete den array Zeiger auf NULL setzen?

also:
delete [] array;
array = NULL;

Sonst wird doch beim nächsten Aufruf von GLfloat* array = new GLfloat[count2] kein neuer Zeiger erzeugt, sondern auf dem alten der neue Speicher allokiert.

Demirug
2003-02-20, 23:04:33
Nein bei C++ muss man Zeiger nicht Null setzten (obwohl man es trotzdem machen sollten). Der Code ist vollkommen richtig. Das Problem muss der Compiler bzw der benutzte Heapmanager sein.

stabilo_boss13
2003-02-21, 09:12:26
Originally posted by Demirug
Das Problem muss der Compiler bzw der benutzte Heapmanager sein.
Den Verdacht habe ich jetzt auch. Hab es nochmal auf XP mit MS VC6 und unter W98 mit DevC++ 4 versucht. Keine Probleme.

Vielleicht solltest du den Compiler nochmal deinstallieren und neu installlieren. Möglicherweise hast du beim Optimieren einen 'Schalter' zu viel umgelegt. Oder versuch es mal mit DevC++ 4.9.7.0 mit dem 'alten' GCC 2.95.3.

Unabhängig davon solltest du aber Speicherbelegungen nie ohne Abfangen möglicher Fehler machen:

std::cout << "allocating " << count2 << " GLfloat!\n";
try {
GLfloat* array = new GLfloat[count2];
delete [] array;
}
catch (...) {
throw;
}
count2 = count2 + 50;

liquid
2003-02-21, 13:27:59
Andere Frage, new gibt doch immer einen Null-Pointer zurück, wenn es keinen Speicher allokieren konnte, oder?

Und delete auf einem Null-Pointer auszuführen ist zwar schwachsinnig, aber im Grunde führt es ja zu keiner "großen" Beeinträchtigung des Programmes. Abstürze, GPFs, etc. Oder sehe ich das falsch?

@Topic: Also ich hab ein wenig rumgeforscht, komischerweise liegt der Fehler aber ganz woanders. Irgendwie erzeuge ich ein Mem-Leak während des Ladens einer TGA (soll als Heightmap benutzt werden). Wenn ich versuche die Heightmap zu laden (was auch keinen Fehler produziert) und danach versuche eine große Menge von GLfloats zu allokieren, dann gibts den dicken GPF. Es gibt keinen GPF wenn ich das Allokieren der GLfloats an den Anfang der Methode der Terrain Klasse packe. Nun könnte ich ja ganz einfach die Allokation verschieben, aber das löst ja nicht das eigentliche Problem. Fakt ist immer noch, dass beim Laden der TGA irgendwas im Speicher "kaputt" geht, was sich bei nachfolgenden Anforderungen via new negativ auswirkt.
Ich werde das mal ausgiebig durchtesten, hoffentlich finde ich da was, sonst bin ich echt aufgeschmissen...

cya
liquid

Demirug
2003-02-21, 13:35:00
delete auf einen NULL-Zeiger geht immer und da passiert auch nichts weiter.

Ob du bei einen new einen NULL-Zeiger bekommst wenn nicht mehr genügend Speicher vorhanden ist hängt vom benutzten Heapmanager ab. Es gibt auch Heapmanager die eine Exception werfen.

Ich glaube nicht das du ein Memleak beim laden der TGA erzeugts den memleak verursachen keine GPF. Es scheint eher so also ob du zuviel Daten in einen Speicherblock schiebst und dir damit den Heap kaputt machst.

zeckensack
2003-02-21, 13:37:30
Bitte den TGA-Ladecode posten.

stabilo_boss13
2003-02-21, 13:42:27
Originally posted by Demirug
Ob du bei einen new einen NULL-Zeiger bekommst wenn nicht mehr genügend Speicher vorhanden ist hängt vom benutzten Heapmanager ab. Es gibt auch Heapmanager die eine Exception werfen.

Stimmt!

Aber ich hab da irgendwie in Erinnerung, dass der Ansi C++ Standard vorgibt, dass eine Exception geworfen werden muss, wenn man einen Fehler beim Allokieren von Speicher hat.

Oder täuscht sich da mein altes Hirn?


Habe es selber gefunden:
The Standard now states that operator new throws an exception of type std::bad_alloc when it fails, rather than returning a NULL pointer.

firewars
2003-02-21, 14:17:08
Warum wird die Windows-Auslagerungsdate eigentlich knapp 2 GB groß, wenn count2 negativ wird?

Unregistered
2003-02-21, 14:24:38
Originally posted by firewars
Warum wird die Windows-Auslagerungsdate eigentlich knapp 2 GB groß, wenn count2 negativ wird?

Das ist ja eine unglaubliche Neuerung, dass unsigned values jetzt negativ werden koennen.

liquid
2003-02-21, 14:49:19
Ausschnitt aus der CPP
void TGAFile::loadTGA(const char* const fileName)
{

if (status == 1)
this->unloadTGA(); // unload currently loaded TGA file

// proceed with file loading
FILE* filePtr; // the file we want to load

// space for garbage data
unsigned char ucharBad;
short int sintBad;

long imageSize;
int colorMode; // 4=RGBA 3=RGB
long imageIdx; // counter
unsigned char colorSwap; // swap var

// open targa
filePtr = fopen(fileName, "rb");

if (filePtr)
{
// file could be opened without error

// read first 2 bytes that we don't need
fread(&ucharBad, sizeof(unsigned char), 1, filePtr);
fread(&ucharBad, sizeof(unsigned char), 1, filePtr);

// read in the image type
fread(&imageTypeCode, sizeof(unsigned char), 1, filePtr);

// check if type is either 2 or 3 (we can handle only these two types)
if ((imageTypeCode != 2) && (imageTypeCode != 3))
fclose(filePtr); // we cant handle this, close file and exit
else
{
// image type can be handled by loader, proceed

// read 13 bytes we don't need
fread(&sintBad, sizeof(short int), 1, filePtr);
fread(&sintBad, sizeof(short int), 1, filePtr);
fread(&ucharBad, sizeof(unsigned char), 1, filePtr);
fread(&sintBad, sizeof(short int), 1, filePtr);
fread(&sintBad, sizeof(short int), 1, filePtr);

// image dimensions
fread(&imageWidth, sizeof(short int), 1, filePtr);
fread(&imageHeight, sizeof(short int), 1, filePtr);

// read bit-depth
fread(&bitCount, sizeof(unsigned char), 1, filePtr);

// garbage data
fread(&ucharBad, sizeof(unsigned char), 1, filePtr);

// colorMode (3=BGR, 4=BGRA)
colorMode = bitCount / 8;
imageSize = imageWidth * imageHeight * colorMode;

imageData = new unsigned char[imageSize]; // alloc mem for image data

// read image data
unsigned long fCount = fread(imageData, sizeof(unsigned char), imageSize, filePtr);

std::cout << "items read: " << fCount << std::endl; // debug

// change BGR to RGB
for (imageIdx = 0; imageIdx < imageSize; imageIdx += colorMode)
{
colorSwap = imageData[imageIdx];
imageData[imageIdx] = imageData[imageIdx + 2];
imageData[imageIdx + 2] = colorSwap;
}

fclose(filePtr);
filePtr = NULL; // secure FILE pointer

status = 1; // loading finished without error
}
}
}

Header:
// fileLoader.h
#ifndef __FILELOADER_H_
#define __FILELOADER_H_

class TGAFile
{
public:
TGAFile();
TGAFile(const char* const fileName);

~TGAFile();

void loadTGA(const char* const fileName);
void unloadTGA();

// methods to get data
unsigned char isTGALoaded() const {return status;}

const unsigned char& getImageTypeCode() const {return imageTypeCode;}

const short int& getImageWidth() const {return imageWidth;}
const short int& getImageHeight() const {return imageHeight;}

const unsigned char& getBitCount() const {return bitCount;}

const unsigned char* const getImageData() const {return imageData;}
unsigned char* getImageDataWritable() const {return imageData;}

private:
unsigned char status; // stores status of TGAFile class

unsigned char imageTypeCode;

// image dimensions
short int imageWidth;
short int imageHeight;

unsigned char bitCount;
unsigned char* imageData; // the real pixels

};



#endif

Xmas
2003-02-21, 17:14:32
Was mir nicht ganz einleuchtet ist wieso du const References auf die Member zurückgibst statt die Werte. Sollten sich die Werte irgendwann unvorhergesehen ändern?

liquid
2003-02-21, 17:34:38
OK, wenn ihr meint dann änder ich das mal schnell. Sonst noch irgendwelche Tipps? Wo bleibt zecki das brain, ich komm hier nicht weiter ;(

Nicht dass nachher noch das passiert: *ocl*
*g*

cya
liquid

OT: Einer ne Ahnung, wie man das hier löst??
2(x-t) = ln(-2x+3)
Bitte nur Umformungen!!

Xmas
2003-02-21, 19:28:59
Originally posted by liquid
OT: Einer ne Ahnung, wie man das hier löst??
2(x-t) = ln(-2x+3)
Bitte nur Umformungen!!
Nach x oder nach t?

liquid
2003-02-21, 19:32:37
Öhh, nach x natürlich! t ist einfach nur eine Konstante. Die Gleichung ist das Ergebnis von zwei Funktionen (e-Funktion und Wurzel-Funktion), die man gleichgesetzt hat. Hatten wir heute in Mathe und selbst unser Lehrer ist dran verzweifelt...

cya
liquid

Xmas
2003-02-21, 20:22:25
Da wird man wohl nur iterativ einen Näherungswert bestimmen können.

liquid
2003-02-21, 20:26:40
Sonst keine Chance da irgendwas algebraisch zu machen?

cya
liquid

ethrandil
2003-02-21, 20:35:13
hab dazu nur gefunden:
[ ln(x) ]' = 1/x

was immer das sagen soll :/ erklären büddä . (Wenn du nix dagegen hast das der Thread ne andere Richtung nimmt ;))

liquid
2003-02-21, 20:37:16
Jojo, das wird wohl die erste Ableitung sein, also Differentialrechnung. Aber das brauch ich hier nicht.
Und solange Zecki sich nicht meldet können wir ja ruhig das Thema etwas wechseln. Ich prockle immer noch in meinem Code rum, auf der Suche nach Schwachstellen. ;D

cya
liquid

EDIT: Jetzt hab ich ganz die Erklärung vergessen. Also stell dir die Funktion vor: f(x) = ln(x)
Wenn wir für x einen Wert einsetzen, dann kriegen wir einen Funktionswert heraus, mit dem wir zB die Funktion zeichnen können. Die Differentialrechnung geht noch einen Schritt weiter, sie will nämlich erfahren, wie groß die Steigung der Funktion an der Stelle x ist. Das macht man mit einer Tangentengleichung, Limes, etc. und irgendwann bekommt man dann die erste "Ableitung" der Funktion raus. wenn man in diese dann den x-Wert einsetzt, dann bekommt man die Steigung an dem Punkt raus.

Xmas
2003-02-22, 01:54:22
Originally posted by liquid
Sonst keine Chance da irgendwas algebraisch zu machen?

cya
liquid
Nein, das geht nur näherungsweise.

zeckensack
2003-02-22, 12:28:48
liquid, bitte heb' mich nicht auf so ein hohes Roß, das steht mir nicht ;)
Andere Anwesende auch sehr gute Progger, ich denke da vor allem an XMas und Demirug :)
Zu deiner TGA-Klasse:
die Ladefunktion sieht sauber aus. Der Fehler muß an anderer Stelle liegen.
Schau bitte mal nach, ob Der Konstruktor von TGAFile 'status' korrekt auf 0 initialisiert.
unloadTGA sowohl den Speicher freigibt, als auch 'status' wieder zurücksetzt. Der Speicher muß mit 'delete[] imageData' freigegeben werden. So und nicht anders
das gleiche gilt für den Destruktor
Bitte nochmal checken daß keine Daten-Zeiger aus der Klasse herauskommen, wenn 'status' nicht 1 ist

Mit letzterem meine ich sowas
unsigned char*
TGAFile::getImageData()
{
if (status!=1) return(NULL);
return(imageData);
}

Ansonsten habe ich noch Vorschläge, wie ich die Klasse ändern würde, aber das ist eher Geschmacksfrage.
isTGALoaded sollte ein bool zurückgeben (klarer, konsistentes Stack-Alignment)
status kann ein bool sein
status könnte sogar gleich ganz entfallen. Wenn imageData zu Beginn im Konstruktor, und immer nach Freigabe des Speichers auf NULL gesetzt wird, kann man statt 'status' einfach 'imageData!=NULL' schreiben. Oder etwas kürzer einfach nur 'imageData'.

liquid
2003-02-22, 13:29:11
Die Änderung hören sich vielversprechend an, das werde ich dann gleich mal machen.

Habe den Fehler mal mit meinen bescheidenen Möglichkeiten noch weiter zurückverfolgt und habe entdeckt, dass er nur dann auftritt, wenn ich Greyscale TGAs zu Laden versuche. Normale Typ2 TGAs (24Bit Farbtiefe) funktionieren einwandfrei, die Typ3 TGAs (8Bit Farbtiefe, Greyscale) machen nur Ärger.
Deshalb vermute ich mal, dass der Fehler da sitzt wo BGR zu RGB umgewandelt wird. Soweit ich das sehe macht die Klassenmethode das ja unabhängig von dem TGA Typ. Wo es bei 24Bit Bitmaps noch sinnvoll ist (obwohl OGL ja auch die umgedrehten Typen versteht) macht es bei Greyscale überhaupt keinen Sinn mehr und macht (mit großer Wahrscheinlichkeit) auch den Heap schrott. Das werde ich wohl ändern, mal sehen ob es den Fehler behebt.
Die Progger können ja mal gucken, ob das wirklich der Fehler sein wird.

Dann habe ich noch versucht meine 512x512 Greyscale Heightmap mit Hilfe von PSP runterzuscalen. Im Bereich von 128x128 Pixels sollte es schon liegen. Lustig ist nun, dass die Originaldatei (die mein Kumpel mir gebastelt hat), die Typ3 ist, beim Speichern mit PSP in eine Typ1 TGA umgewandelt wird auch wenn ich alles richtig eingestellt habe (8Bit, Unkomprimiert). Typ1 ist irgendwas mit Color-Map oder so, jedenfalls kann ich es nicht laden. Frage ist nur warum PSP die Datei mir einer Color-Map speichert, die die Datei nachher größer macht, als sie vorher war (wenn ich nicht runterscale dann macht er den Blödsinn auch). Eine ne' Ahnung? Oder ein kleines Freeware/Opensource Tool was TGAs konvertiert?

cya
liquid

EDIT:
Soviele Fragen, also füg ich gleich noch eine hinzu. Also nehmen wir mal an ich habe meine 8Bit TGA geladen, die Pixels befinden sich jetzt irgendwo im Speicher, mein Heap ist glücklicherweise nicht kaputt gegangen, die GraKa funzt und mein Monitor ist noch nicht explodiert (also alles im grünen Bereich). Wie genau erzeuge ich jetzt aus diesen Graustufen-Pixels eine OGL-Textur?


GLuint texture; // enthält die Textur

TGAFile myTGA("data/hmapOriginal.tga"); // lade die TGA

glGenTextures(1, &texture); // Platz für eine OGL Textur

// texture 1
glBindTexture(GL_TEXTURE_2D, texture);
// generate the texture
glTexImage2D(GL_TEXTURE_2D, 0, ?, myTGA.getImageWidth(), myTGA.getImageHeight(), 0, ?, GL_UNSIGNED_BYTE, myTGA.getImageData());

// nearest filtering
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);


Frage, was soll ich bei den Fragezeichen reinschreiben?? GL_LUMINANCE8?? Oder GL_R3_G3_B2? Oder was unterschiedliches? Luminance ist doch Leuchtintensität oder nicht? Dann würde das doch ganz gut passen. Oder verändert die Textur dann nur die Einwirkungen einer Lichtquelle? Kann ich mir nicht vorstellen, dafür ist ja schließlich das "Material" der Fläche zuständig. Und was hat er mit diesem PixelUnpacking auf sich? Das ist ja standardmäßig auf 4 gestellt, muß das jetzt auf 1 gestellt werden (die Pixels sind ja alle an einem Byte ausgerichtet)??
Frage über Fragen... *g*

firewars
2003-02-22, 18:58:59
Originally posted by Unregistered


Das ist ja eine unglaubliche Neuerung, dass unsigned values jetzt negativ werden koennen.

Wer spricht von unsigned variables? ;)
Nein, ernsthaft: ich habs so umgeschrieben, dass die Variable auch negativ seien konnte. Aber was solls.

ethrandil
2003-02-22, 19:11:00
Originally posted by firewars


Wer spricht von unsigned variables? ;)
ich habs so umgeschrieben, dass die Variable auch negativ seien konnte.
Naja, eine signed variable (zB -1) ist binär (bei 16 bit)
1000000000000001
Das ist in unsigned ... mehr ;)

Xmas
2003-02-22, 19:24:44
Originally posted by ethrandil
Naja, eine signed variable (zB -1) ist binär (bei 16 bit)
1000000000000001
Das ist in unsigned ... mehr ;)
Nein, -1 in Zweierkomplementdarstellung sind immer nur Einsen, also bei 16 Bit 1111111111111111 ;)

Unregistered
2003-02-22, 22:06:58
@ Liquid:
ad 1: Das umwandeln von BGR zu RGB ist auf 24 bit (3 byte pro pixel) ausgerichtet. Wenn du jetzt ein TGA mit 8 bit (1 ybte pro Pixel) lädst, dann greifst du spätestens beim letzten Pixel mit

imageData[imageIdx + 2] = colorSwap;

in die große Leere...
Einfdach eine Abfrage einfügen
[code]
if (bitcount==8)
{

Unregistered
2003-02-22, 22:23:34
@ Liquid:
ad 1: Das umwandeln von BGR zu RGB ist auf 24 bit (3 byte pro pixel) ausgerichtet. Wenn du jetzt ein TGA mit 8 bit (1 ybte pro Pixel) lädst, dann greifst du spätestens beim letzten Pixel mit

imageData[imageIdx + 2] = colorSwap;

in die große Leere...Kann sein dass das später ein Problem macht.
Einfach eine Abfrage einfügen

if (bitcount==8)
{
tatütata;
}


ad 2:
Beim ersten Fragzeichen kommt das interne Format hin. (Was genau das ist weiß ich auch nicht, ich nehme an es bezeichnet das Format in dem die einzelnen Pixel im Framebuffer liegen) Das kann man auf 4 lassen. (-> entspricht AFAIK GL_RGBA)
Das zweite Fragezeichen bezeichnet das Format der hereinkommenden Daten. Bei Graustufentexturen bietet sich GL_LUMINANCE an, wie du schon vermutet hast. Der hereinkommende Wert wird einfach dreimal auf R G und B kopiert, (für Alpha kommt 1.0 dazu) und schon hast du einen Frambufferverträglichen Grauton.

Hope that helps

ethrandil
2003-02-23, 00:38:22
Originally posted by Xmas

Nein, -1 in Zweierkomplementdarstellung sind immer nur Einsen, also bei 16 Bit 1111111111111111 ;)
Echt? hmm ich dachte bei negativen zahlen ist nur das erste bit ausschlaggebend und der rest halt einfach ne 15 bit zahl ... nagut, so kann man sich täuschen...

MadMax69
2003-02-23, 01:44:34
Echt? hmm ich dachte bei negativen zahlen ist nur das erste bit ausschlaggebend und der rest halt einfach ne 15 bit zahl ... nagut, so kann man sich täuschen...

Es gibt beide möglichkeiten wobei in Rechnern das Zweierkomplement verwendet wird.

Abe Ghiran
2003-02-23, 01:51:54
Originally posted by ethrandil

Echt? hmm ich dachte bei negativen zahlen ist nur das erste bit ausschlaggebend und der rest halt einfach ne 15 bit zahl ... nagut, so kann man sich täuschen...

Das ist dann das Einerkomplement -> das vorderste bit gibt das Vorzeichen an. Also bei einer 8 bit Zahl hat man das Vorzeichen und dann 7bit für Informationen, das entspricht einem Wertebereich von -127 bis +127. Dabei hat man aber das Problem das man für die Null zwei Darstellungen hat (10000000 und 00000000), außerdem kann man damit nicht so schön rechnen.

Deshalb nimmt man i.R. das Zweierkomplement, wie MadMax69 ja schon gesagt hat. Beim Zweierkomplement entsprechen die positiven Zahlen denen im Einerkomplement. Für negative Zahlen invertiert man die positive Gegenzahl und rechnet dann noch eine 1 dazu.
Mal als Beispiel +2 im Zweierkomplement: 00000010 (simpel)
-2 im Zweierkomplement: Man nimmt die positive Zahl (00000010), invertiert die (11111101) und rechnet noch 1 dazu -> 11111110.

Edit: So auch nicht ganz richtig, siehe dazu Magnum's post weiter unten ;).

Grüße, Jan

zeckensack
2003-02-23, 11:36:43
Originally posted by liquid
Frage, was soll ich bei den Fragezeichen reinschreiben?? GL_LUMINANCE8?? Oder GL_R3_G3_B2? Oder was unterschiedliches? Luminance ist doch Leuchtintensität oder nicht? Dann würde das doch ganz gut passen. Oder verändert die Textur dann nur die Einwirkungen einer Lichtquelle? Kann ich mir nicht vorstellen, dafür ist ja schließlich das "Material" der Fläche zuständig. Und was hat er mit diesem PixelUnpacking auf sich? Das ist ja standardmäßig auf 4 gestellt, muß das jetzt auf 1 gestellt werden (die Pixels sind ja alle an einem Byte ausgerichtet)??
Frage über Fragen... *g*

Erstes Fragezeichen: GL_LUMINANCE
Zweites Fragezeichen: GL_RED

Das zweite erscheint auf den ersten Blick falsch, isses aber nicht :)

Du hättest übrigens noch (für's erste) GL_INTENSITY zur Auswahl. Der Unterschied zw intensity und luminance ist, daß eine intensity-Textur sich wie eine RGBA-Textur verhält, bei der alle Komponenten (auch Alpha) gleich sind. Luminance-Texturen verhalten sich wie RGB-Texturen, und haben immer volles Alpha (ie nicht-transparent).

Unregistered
2003-02-23, 19:57:32
Originally posted by zeckensack


Erstes Fragezeichen: GL_LUMINANCE
Zweites Fragezeichen: GL_RED

Das zweite erscheint auf den ersten Blick falsch, isses aber nicht :)

Du hättest übrigens noch (für's erste) GL_INTENSITY zur Auswahl. Der Unterschied zw intensity und luminance ist, daß eine intensity-Textur sich wie eine RGBA-Textur verhält, bei der alle Komponenten (auch Alpha) gleich sind. Luminance-Texturen verhalten sich wie RGB-Texturen, und haben immer volles Alpha (ie nicht-transparent).

Wuz? GL_RED? Wieso das denn?

Magnum
2003-02-24, 13:23:25
Originally posted by Abe Ghiran


Das ist dann das Einerkomplement -> das vorderste bit gibt das Vorzeichen an. Also bei einer 8 bit Zahl hat man das Vorzeichen und dann 7bit für Informationen, das entspricht einem Wertebereich von -127 bis +127. Dabei hat man aber das Problem das man für die Null zwei Darstellungen hat (10000000 und 00000000), außerdem kann man damit nicht so schön rechnen.

Das ist aber die Darstellung mit Vorzeichen! Ein Bit Vorzeichen (0="+", 1="-") und 15 Bit Integer-Zahl.

Das Einserkomplement erhält man, wenn man alle Bits invertiert!
Bsp: 6 = 00000110, -6 = 11111001

Fürs Zweierkomplement einfach noch ne 1 hinzuaddieren!
-6 = 11111010

Abe Ghiran
2003-02-24, 13:39:39
:bonk: Da hast du natürlich recht. Aber Rechnerstrukturen ist schon etwas her und außerdem war es bei dem posting ja schon spät am Tag ;).

Jan