Advertisement Jump to content
  • Advertisement


  • Content Count

  • Joined

  • Last visited

Community Reputation

1918 Excellent

1 Follower

About rnlf_in_space

  • Rank

Personal Information

  • Role
  • Interests


  • Twitter
  • Github

Recent Profile Visitors

The recent visitors block is disabled and is not being shown to other users.

  1. While I understand what you're aiming at, in the absolute way you state this, it's not right. There are circumstances where volatile is the right thing to use. It is unlikely for a game developer on modern hardware to ever be in such circumstances, but there are areas of software engineering, where it's the right thing to do (embedded/low level software, retro hardware games). Basically whenever dealing with memory that is not under the control of your program (hardware registers, memory mapped IO). If you see a volatile in high level code for modern hardware, you most likely have a bug 😝
  2. rnlf_in_space

    Temporary string literals

    @ryt, just to be clear, what @Bregma suggested is a joke. You see how they want you to "XOR with the original string"? That means you need to store that in your file.
  3. rnlf_in_space

    Temporary string literals

    @Alberth, I think what they're really trying to do is to have constant string data in a program without having it in any file they're shipping. I'm a bit lost as to how to explain that that's not possible.
  4. rnlf_in_space

    Temporary string literals

    So it's still stored inside the exe, just in this case as part of a movl instruction. That works for short strings (8 characters incl. terminator at most). This is the piece of code that copies the string onto the stack! Yes, 0x00636261 is a 32 bit value that is equal to the string "ABC\0". So yes, for short strings it's part of the code itself. But that doesn't work with longer strings. When you have a longer string, it will copy it from where it is stored (.rodata or .text doesn't really matter) onto the stack first. See it here: The .LCn: are the labels where the compiler puts the string data, all those movdqa xmm0 ... movaps [rsp] are the unrolled memcpy, where the compiler added the code to move the string from the (in this case) .text section onto the stack. The first line, sub rsp, 104 is where the compiler makes space for the string on the stack. The stack is completely empty when the program starts running. The only way to get something onto the stack is during runtime using code! The same goes for the heap. You cannot store something on the stack or heap directly so that it's just there when your program starts running.
  5. rnlf_in_space

    Temporary string literals

    No, it's the same, really. Going back to the moving apartments analogy, if you want to sort the books into your shelves (the stack in your code) in the new apartment, you first have to get them there somehow. .text and .rodata both end up in the exe (and again, this would put the strings into the read only data section, not the code section). The only way you get something onto the stack or heap is to put it there using code (that the compiler generates for you, you don't see it directly in C++). And that generated code needs to copy it from somewhere. This "somewhere" is you exe file. I cannot ask you to hand me a certain book from your bookshelves if you didn't bring that book from your old apartment. And that means you need to have had that book in one of the boxes while moving. The exe file must contain all the data required to execute your program (unless you load the data from a different file, but then again you need to ship that file and it doesn't make a big difference in the overall size of things). If your program contains code that relies on a certain string being present, then that string must somehow get to the place where you execute the program.
  6. rnlf_in_space

    Temporary string literals

    If the strings get used (and not optimized out), of course they need to be stored somewhere. Where else would they be stored if not in the executable? You could store them in a data file, but then you have to load them at runtime. I don't know how to clarify that any better... if the strings are used OF COURSE they need to be stored somewhere, how else could you use them? Maybe an analogy: If you move to a different apartment and you want to take your books with you, you have to store them in a box. Are the boxes "bloated" just because you want to take your 10000 books with you? Your new apartment is the running process, the boxes are the executable file, the books are the strings. If you don't want the bloat, find a way to code your program without using the strings.
  7. rnlf_in_space

    Temporary string literals

    Of course the string has to be stored somewhere in your executable file, likely in a readonly data section, as you conjectured. The heap is a purely runtime thing and will only be populated during execution of your program. That being said, depending on what you're doing with the string and your optimization options, it's possible that the string doesn't actually end up on the heap (e.g. all functions you call on the string are getting inlined and you only do read-only accesses).
  8. rnlf_in_space

    Array arithmetic

    Could be a way to gauge how careful your coworkers do their reviews.
  9. rnlf_in_space

    How to organize constants? (c++)

    suliman, because it doesn't protect you from type errors. enum WeaponClass { Axe, Sword }; enum Action { Move, SkipTurn }; if(unit.action == Axe) // perfectly fine, but still not what you want And in the end you'll want to prefix the names, because now they are not scoped anymore, imagine this: enum WeaponClass { Axe, Sword, }; enum ImpactSound { Axe, // error, Axe already defined Sword // error, Sword already defined }; The classic way to fix that would be to prefix the enumerators: enum WeaponClass { WeaponAxe, WeaponSword, }; enum ImpactSound { ImpactSoundAxe, ImpactSoundSword }; And that's already almost the scoped/typed enum variant.
  10. rnlf_in_space

    How to organize constants? (c++)

    For one, it's called constexpr in a single word. Second, it the advantage of using a typed enum is type safety. Using integers for everything makes the code less easy to understand and easier to confuse different things: constexpr int WEAPON_AXE = 1; constexpr int WEAPON_SWORD = 2; constexpr int ACTION_MOVE = 3; if(unit.action == WEAPON_AXE) { // allowed by the compiler, but clearly not what you want. // something like this will happen sooner or later. Maybe not in an if statement, but // I've seen it happen dozens of times when passing method arguments. // And when it happens, it can be a pain to debug. } enum class WeaponClass { Axe, Sword }; enum class Action { Move, SkipTurn }; if(unit.action == WeaponClass:Axe) // compiler error If you really want to express a number (like mr_tawan's example in the beginning), then a constexpr is a good way to do it. You'll have to make it a static constexpr though, if you want to define it in a header file, or else you will get into trouble when linking.
  11. rnlf_in_space

    How to organize constants? (c++)

    In modern C++, the normal way to do that would be a strongly typed enum like so: enum class WeaponClass { Sword, Axe }; if(weapon.class == WeaponClass::Axe) { ... }
  12. rnlf_in_space

    loop only every 10th or so

    Of course you get flickering when you draw something only every 10th frame. What you probably want to do is store the last computed FPS into a variable and only do the computation every 10th frame, but still draw on every frame.
  13. rnlf_in_space

    How was lighting handled in early 3D games?

    Don't forget that Duke Nukem 3D was released 3 years after DOOM. Half a year before id released Quake. Of course Build engine games looked better at that time.
  14. rnlf_in_space

    Always align memory in array class ?

    Alignment is important for many things. Most CPUs cannot access unaligned memory. If you want to save on the padding, try rearranging stuff inside of your elements or consider going from Array of Structures to a Structure of Arrays, i.e. instead of having struct MyStruct { uint32_t foo; uint16_t bar; }; MyStruct array[100]; // 200 bytes wasted To something like struct MyData { uint32_t foo[100]; uint16_t bar[100]; }; MyData data; // Nothing wasted.
  • Advertisement

Important Information

By using, you agree to our community Guidelines, Terms of Use, and Privacy Policy. is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!