Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Special Interest Groups
  3. C++ Gurus
  4. The Question of a Lifetime
Forum Updated to NodeBB v4.3 + New Features

The Question of a Lifetime

Scheduled Pinned Locked Moved Unsolved C++ Gurus
5 Posts 4 Posters 611 Views 3 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • J.HilkJ Offline
    J.HilkJ Offline
    J.Hilk
    Moderators
    wrote on last edited by
    #1

    We all should know, QByteArray::fromRawData is to be used with care, pre and hindsight.

    But I don't know enough about constexpr to judge if the lifetime of this char data is guaranteed under all circumstances:

    void Class::onFunction() noexcept
    {
        constexpr char serialNumberCommand[] = "\x11\x01\x1E\xD0";
        emit writeRawData(QByteArray::fromRawData(serialNumberCommand, sizeof(serialNumberCommand)));
    }
    
    

    Anyone with answers and/or opinions is welcome :D


    Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


    Q: What's that?
    A: It's blue light.
    Q: What does it do?
    A: It turns blue.

    JonBJ 1 Reply Last reply
    0
    • J.HilkJ J.Hilk

      We all should know, QByteArray::fromRawData is to be used with care, pre and hindsight.

      But I don't know enough about constexpr to judge if the lifetime of this char data is guaranteed under all circumstances:

      void Class::onFunction() noexcept
      {
          constexpr char serialNumberCommand[] = "\x11\x01\x1E\xD0";
          emit writeRawData(QByteArray::fromRawData(serialNumberCommand, sizeof(serialNumberCommand)));
      }
      
      

      Anyone with answers and/or opinions is welcome :D

      JonBJ Offline
      JonBJ Offline
      JonB
      wrote on last edited by
      #2

      @J-Hilk
      I would say "no", though it might work. I would refer you to e.g. https://stackoverflow.com/a/13867690/489865

      The short answer is that not only is static useful, it is pretty well always going to be desired.

      First, note that static and constexpr are completely independent of each other. static defines the object's lifetime during execution; constexpr specifies that the object should be available during compilation. Compilation and execution are disjoint and discontiguous, both in time and space. So once the program is compiled, constexpr is no longer relevant.

      Every variable declared constexpr is implicitly const but const and static are almost orthogonal (except for the interaction with static const integers.)

      constexpr is only a compile-time thing. You can't be sure what code is generated. You need to guarantee the lifetime of char serialNumberCommand[]. As it stands serialNumberCommand[] may only be a local variable which gets initialised each time and destroyed at end of function. It is the static you need for persistence. At which point the constexpr isn't relevant since the compiler does not need to know the value of that string. So static constexpr if you want, but static alone should be equally good.

      J.HilkJ 1 Reply Last reply
      2
      • JonBJ JonB

        @J-Hilk
        I would say "no", though it might work. I would refer you to e.g. https://stackoverflow.com/a/13867690/489865

        The short answer is that not only is static useful, it is pretty well always going to be desired.

        First, note that static and constexpr are completely independent of each other. static defines the object's lifetime during execution; constexpr specifies that the object should be available during compilation. Compilation and execution are disjoint and discontiguous, both in time and space. So once the program is compiled, constexpr is no longer relevant.

        Every variable declared constexpr is implicitly const but const and static are almost orthogonal (except for the interaction with static const integers.)

        constexpr is only a compile-time thing. You can't be sure what code is generated. You need to guarantee the lifetime of char serialNumberCommand[]. As it stands serialNumberCommand[] may only be a local variable which gets initialised each time and destroyed at end of function. It is the static you need for persistence. At which point the constexpr isn't relevant since the compiler does not need to know the value of that string. So static constexpr if you want, but static alone should be equally good.

        J.HilkJ Offline
        J.HilkJ Offline
        J.Hilk
        Moderators
        wrote on last edited by
        #3

        @JonB said in The Question of a Lifetime:

        https://stackoverflow.com/a/13867690/489865

        you're right, static is probably the way I should go.

        But I dislike static and wanted to explore new fancy ways!!! :D


        Be aware of the Qt Code of Conduct, when posting : https://forum.qt.io/topic/113070/qt-code-of-conduct


        Q: What's that?
        A: It's blue light.
        Q: What does it do?
        A: It turns blue.

        1 Reply Last reply
        0
        • S Offline
          S Offline
          SimonSchroeder
          wrote on last edited by
          #4

          It might work right now, but will not in the future.

          There is a new feature coming to C++26 (https://www.open-std.org/jtc1/sc22/wg21/docs/papers/2023/p2795r3.html) which addresses a problem related to this. Currently if you do something like this

          void f()
          {
              const char password[] = "secret";
          }
          
          void g()
          {
              char str[7];
              std::cout << str << '\n';
          }
          
          int main()
          {
              f();
              g();
          }
          

          it will most likely print secret. Both functions will use the same stack space and reuse the same memory. The proposal for C++26 is to handle uninitialized variables explicitly to avoid this problem.

          On the other hand this also means in your concrete case if some other function reuses the same stack space it will overwrite \x11\x01\x1E\xD0.

          Someone should check the following with the standard, but I believe there is a difference between

          char serialNumberCommand[] = "\x11\x01\x1E\xD0";
          

          and

          char *serialNumberCommand = "\x11\x01\x1E\xD0";
          

          I would expect the first version to copy the string into the serialNumberCommand array. In the latter case you are just holding a pointer to an existing string in static storage. This pointer can then be handed safely to QByteArray::fromRawData as QByteArray will not hold the pointer handed to it, but the thing it points to. The thing it points to should be permanent. (I am not sure it the C++ standard guarantees this, but it is the general implementation of C strings.)

          If you want something more fancy, there is not only constexpr but also constinit (since C++20). cppreference (https://en.cppreference.com/w/cpp/language/constinit) mentions that constinit declares a variable with static or thread storage duration. However, as the example on that page shows, you need to write static constinit inside a function. Just constinit alone will not do.

          1 Reply Last reply
          3
          • Kent-DorfmanK Offline
            Kent-DorfmanK Offline
            Kent-Dorfman
            wrote on last edited by
            #5

            @SimonSchroeder
            Your description above is in substance, correct. I had to check it to make sure myself. ;^) By assigning the string literal to an array (const or not) it is considered "auto class". When you create a pointer to the string literal the pointer will "typically" point to a RO-data segment containing the literal.

            1 Reply Last reply
            0

            • Login

            • Login or register to search.
            • First post
              Last post
            0
            • Categories
            • Recent
            • Tags
            • Popular
            • Users
            • Groups
            • Search
            • Get Qt Extensions
            • Unsolved