Exposing globals as read-only

Discussion in 'C Programming' started by Ark Khasin, Mar 10, 2008.

  1. Ark Khasin

    Ark Khasin Guest

    Consider a problem of exposing some
    T foo;
    for read-only access by other modules, in order to prevent inadvertent
    (as opposed to malicious) writes to it. I cannot afford and/or do not
    want to incur the overhead of access functions. A solution could be:

    foo.h:
    extern T foo;
    #define foo ((const T)foo) //hide the original foo

    foo.c:
    #include "foo.h"
    #undef foo
    T foo;

    There can be variations on this theme avoiding the often deprecated
    #undef, like
    foo.h:
    extern T foo;
    #ifndef OWNER_foo
    #define foo ((const T)foo) //hide the original foo
    #endif

    foo.c:
    #define OWNER_foo
    #include "foo.h"
    T foo;

    What are NG's opinions on whether
    - it looks right aesthetically
    - it is a good idea to "overload" the identifier
    - this can be a recommended practice (pattern) for a company's coding
    standard
    - (probably OT) this can confuse popular or bundled code browsers,
    debuggers etc

    --
    Thank you,
    Ark
     
    Ark Khasin, Mar 10, 2008
    #1
    1. Advertising

  2. Ark Khasin wrote:
    > Consider a problem of exposing some
    > T foo;
    > for read-only access by other modules, in order to prevent inadvertent
    > (as opposed to malicious) writes to it. I cannot afford and/or do not
    > want to incur the overhead of access functions. A solution could be:
    >
    > foo.h:
    > extern T foo;
    > #define foo ((const T)foo) //hide the original foo
    >
    > foo.c:
    > #include "foo.h"
    > #undef foo
    > T foo;
    >
    > There can be variations on this theme avoiding the often deprecated
    > #undef, like
    > foo.h:
    > extern T foo;
    > #ifndef OWNER_foo
    > #define foo ((const T)foo) //hide the original foo
    > #endif
    >
    > foo.c:
    > #define OWNER_foo
    > #include "foo.h"
    > T foo;
    >
    > What are NG's opinions on whether
    > - it looks right aesthetically
    > - it is a good idea to "overload" the identifier
    > - this can be a recommended practice (pattern) for a company's coding
    > standard
    > - (probably OT) this can confuse popular or bundled code browsers,
    > debuggers etc
    >
    > --
    > Thank you,
    > Ark


    I wonder if it would work to do something like:

    extern const T foo;

    --
    --Falcon Kirtaran
     
    Falcon Kirtaran, Mar 10, 2008
    #2
    1. Advertising

  3. Ark Khasin

    Ark Khasin Guest

    Falcon Kirtaran wrote:
    > Ark Khasin wrote:
    >> Consider a problem of exposing some
    >> T foo;
    >> for read-only access by other modules, in order to prevent inadvertent
    >> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >> want to incur the overhead of access functions. A solution could be:
    >>
    >> foo.h:
    >> extern T foo;
    >> #define foo ((const T)foo) //hide the original foo
    >>
    >> foo.c:
    >> #include "foo.h"
    >> #undef foo
    >> T foo;
    >>
    >> There can be variations on this theme avoiding the often deprecated
    >> #undef, like
    >> foo.h:
    >> extern T foo;
    >> #ifndef OWNER_foo
    >> #define foo ((const T)foo) //hide the original foo
    >> #endif
    >>
    >> foo.c:
    >> #define OWNER_foo
    >> #include "foo.h"
    >> T foo;
    >>
    >> What are NG's opinions on whether
    >> - it looks right aesthetically
    >> - it is a good idea to "overload" the identifier
    >> - this can be a recommended practice (pattern) for a company's coding
    >> standard
    >> - (probably OT) this can confuse popular or bundled code browsers,
    >> debuggers etc
    >>

    >
    > I wonder if it would work to do something like:
    >
    > extern const T foo;
    >

    No: foo.c would have a conflict between the definition and the
    declaration. Fooling the compiler by not including foo.h not only is
    bad, but also causes UB (most likely, a linker's complaint)
    --
    Ark
     
    Ark Khasin, Mar 10, 2008
    #3
  4. Ark Khasin

    Ian Collins Guest

    Ark Khasin wrote:
    > Consider a problem of exposing some
    > T foo;
    > for read-only access by other modules, in order to prevent inadvertent
    > (as opposed to malicious) writes to it. I cannot afford and/or do not
    > want to incur the overhead of access functions. A solution could be:
    >

    Provide an inline function in a header.

    --
    Ian Collins.
     
    Ian Collins, Mar 10, 2008
    #4
  5. Ark Khasin

    Shri Guest

    Can this be done???

    Put all the functions who want Write access to this global variable in
    a different file, and make the variable "global static". so now the
    variable is visible only to the functions that are defined in the new
    file.

    Now to give other modules read access, put a function in the new file
    which when called will just return the value of the global variable (I
    think this is not a big overhead).

    Example:

    New.c

    static int Variable; // this is a global static variable and hence it
    is visible only to the functions defined in this same file.

    Func1()
    {

    .....
    ;;;;

    }

    //All functions which need write access

    int GetVarValue()
    {
    return Variable;
    }


    Foo.c

    int GetVarValue();

    Func00()
    {

    ....
    ;;;

    }

    //All functions that do not need write access to the global variable.
     
    Shri, Mar 10, 2008
    #5
  6. Ark Khasin

    Ark Khasin Guest

    Ian Collins wrote:
    > Ark Khasin wrote:
    >> Consider a problem of exposing some
    >> T foo;
    >> for read-only access by other modules, in order to prevent inadvertent
    >> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >> want to incur the overhead of access functions. A solution could be:
    >>

    > Provide an inline function in a header.
    >

    How does it hide the variable from inadvertent write access?
    -- Ark
     
    Ark Khasin, Mar 10, 2008
    #6
  7. Ark Khasin

    Ark Khasin Guest

    Shri wrote:
    >
    > Now to give other modules read access, put a function in the new file
    > which when called will just return the value of the global variable (I
    > think this is not a big overhead).
    >

    The whole point of the exercise is to avoid access functions.
    -- Ark
     
    Ark Khasin, Mar 10, 2008
    #7
  8. Ark Khasin

    Ian Collins Guest

    Ark Khasin wrote:
    > Shri wrote:
    >>
    >> Now to give other modules read access, put a function in the new file
    >> which when called will just return the value of the global variable (I
    >> think this is not a big overhead).
    >>

    > The whole point of the exercise is to avoid access functions.


    Why?

    --
    Ian Collins.
     
    Ian Collins, Mar 10, 2008
    #8
  9. Ark Khasin

    Ian Collins Guest

    Ark Khasin wrote:
    > Ian Collins wrote:
    >> Ark Khasin wrote:
    >>> Consider a problem of exposing some
    >>> T foo;
    >>> for read-only access by other modules, in order to prevent inadvertent
    >>> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >>> want to incur the overhead of access functions. A solution could be:
    >>>

    >> Provide an inline function in a header.
    >>

    > How does it hide the variable from inadvertent write access?


    You don't expose the variable, just the function that returns its value.

    --
    Ian Collins.
     
    Ian Collins, Mar 10, 2008
    #9
  10. Ark Khasin

    Ark Khasin Guest

    Ian Collins wrote:
    > Ark Khasin wrote:
    >> Ian Collins wrote:
    >>> Ark Khasin wrote:
    >>>> Consider a problem of exposing some
    >>>> T foo;
    >>>> for read-only access by other modules, in order to prevent inadvertent
    >>>> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >>>> want to incur the overhead of access functions. A solution could be:
    >>>>
    >>> Provide an inline function in a header.
    >>>

    >> How does it hide the variable from inadvertent write access?

    >
    > You don't expose the variable, just the function that returns its value.
    >

    I may be thick but I don't know how an inline function would know what
    the variable is unless it's declared... Could you please offer a snippet
    of code?
    -- Ark
     
    Ark Khasin, Mar 10, 2008
    #10
  11. Ark Khasin

    Ark Khasin Guest

    Ian Collins wrote:
    > Ark Khasin wrote:
    >> Shri wrote:
    >>> Now to give other modules read access, put a function in the new file
    >>> which when called will just return the value of the global variable (I
    >>> think this is not a big overhead).
    >>>

    >> The whole point of the exercise is to avoid access functions.

    >
    > Why?
    >

    Because of the overhead perhaps? Breaking the instructions pipeline
    (twice) for no intrinsic value...
     
    Ark Khasin, Mar 10, 2008
    #11
  12. Ark Khasin

    Ian Collins Guest

    Ark Khasin wrote:
    > Ian Collins wrote:
    >> Ark Khasin wrote:
    >>> Ian Collins wrote:
    >>>> Ark Khasin wrote:
    >>>>> Consider a problem of exposing some
    >>>>> T foo;
    >>>>> for read-only access by other modules, in order to prevent inadvertent
    >>>>> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >>>>> want to incur the overhead of access functions. A solution could be:
    >>>>>
    >>>> Provide an inline function in a header.
    >>>>
    >>> How does it hide the variable from inadvertent write access?

    >>
    >> You don't expose the variable, just the function that returns its value.
    >>

    > I may be thick but I don't know how an inline function would know what
    > the variable is unless it's declared... Could you please offer a snippet
    > of code?


    You're not, I am....

    --
    Ian Collins.
     
    Ian Collins, Mar 10, 2008
    #12
  13. Ark Khasin wrote:
    > Ian Collins wrote:
    >> Ark Khasin wrote:
    >>> Ian Collins wrote:
    >>>> Ark Khasin wrote:
    >>>>> Consider a problem of exposing some
    >>>>> T foo;
    >>>>> for read-only access by other modules, in order to prevent inadvertent
    >>>>> (as opposed to malicious) writes to it. I cannot afford and/or do not
    >>>>> want to incur the overhead of access functions. A solution could be:
    >>>>>
    >>>> Provide an inline function in a header.
    >>>>
    >>> How does it hide the variable from inadvertent write access?

    >>
    >> You don't expose the variable, just the function that returns its value.
    >>

    > I may be thick but I don't know how an inline function would know what
    > the variable is unless it's declared... Could you please offer a snippet
    > of code?
    > -- Ark


    Generally, that looks something like:

    inline T getfoo() { return foo; };

    This function goes into the file where foo is declared, after the
    declaration, so it does know about it.

    --
    --Falcon Kirtaran
     
    Falcon Kirtaran, Mar 10, 2008
    #13
  14. In article <_p4Bj.5461$Y33.4853@trndny07>,
    Ark Khasin <> wrote:

    >I may be thick but I don't know how an inline function would know what
    >the variable is unless it's declared...


    Obviously it can't, but if you're only trying to protect against
    inadvertent modification you could give the variable an obscure name
    and the inline function a short, natural, documented one.

    -- Richard
    --
    :wq
     
    Richard Tobin, Mar 10, 2008
    #14
  15. Ark Khasin <> writes:

    > Consider a problem of exposing some
    > T foo;
    > for read-only access by other modules, in order to prevent inadvertent
    > (as opposed to malicious) writes to it. I cannot afford and/or do not
    > want to incur the overhead of access functions. A solution could be:
    >
    > foo.h:

    <snip pre-processor based solution>
    > What are NG's opinions on whether
    > - it looks right aesthetically
    > - it is a good idea to "overload" the identifier
    > - this can be a recommended practice (pattern) for a company's coding
    > standard
    > - (probably OT) this can confuse popular or bundled code browsers,
    > debuggers etc


    Forgive me for no answering these questions but I'd suggest you
    consider:

    foo.h:
    extern const T *foop;

    and in foo.c:

    static T foo = {/* stuff */};
    const T *foop = &foo;

    It costs you a dereference, and may not fit your problem (since I
    suspect you may have a reason not to change the way foo is currently
    accessed) but it has the benefit of simplicity. Anyway, posted just
    in case you can change the accesses.

    --
    Ben.
     
    Ben Bacarisse, Mar 10, 2008
    #15
  16. Ark Khasin

    Jack Klein Guest

    On Mon, 10 Mar 2008 02:19:49 GMT, Ark Khasin
    <> wrote in comp.lang.c:

    > Consider a problem of exposing some
    > T foo;
    > for read-only access by other modules, in order to prevent inadvertent
    > (as opposed to malicious) writes to it. I cannot afford and/or do not
    > want to incur the overhead of access functions. A solution could be:
    >
    > foo.h:
    > extern T foo;
    > #define foo ((const T)foo) //hide the original foo
    >
    > foo.c:
    > #include "foo.h"
    > #undef foo
    > T foo;
    >
    > There can be variations on this theme avoiding the often deprecated
    > #undef, like
    > foo.h:
    > extern T foo;
    > #ifndef OWNER_foo
    > #define foo ((const T)foo) //hide the original foo
    > #endif
    >
    > foo.c:
    > #define OWNER_foo
    > #include "foo.h"
    > T foo;
    >
    > What are NG's opinions on whether
    > - it looks right aesthetically
    > - it is a good idea to "overload" the identifier
    > - this can be a recommended practice (pattern) for a company's coding
    > standard
    > - (probably OT) this can confuse popular or bundled code browsers,
    > debuggers etc


    The best esthetic solution I ever came up for was a case like this:

    static T foo;
    const T* read_foo = &foo;

    ....and of course, in a header file:

    extern const T* read_foo;

    This allows clients read-only access to foo by dereferencing the
    pointer. It does not protect against malicious modification, since
    there is no undefined behavior in casting away const qualification if
    the actual object was defined non constant. But it does object to
    accidental modification, which you say is your objective.

    I occasionally use this in places where the overhead of a function
    call would be burdensome, as inside ISRs.

    --
    Jack Klein
    Home: http://JK-Technology.Com
    FAQs for
    comp.lang.c http://c-faq.com/
    comp.lang.c++ http://www.parashift.com/c -faq-lite/
    alt.comp.lang.learn.c-c++
    http://www.club.cc.cmu.edu/~ajo/docs/FAQ-acllc.html
     
    Jack Klein, Mar 11, 2008
    #16
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. vnssoftware
    Replies:
    4
    Views:
    474
    Dmitry R
    Dec 31, 2003
  2. keithb
    Replies:
    2
    Views:
    8,035
    keithb
    Jun 7, 2006
  3. Phillip Vong

    VS2005 - Run Code only in Read Only mode.

    Phillip Vong, Apr 6, 2007, in forum: ASP .Net
    Replies:
    0
    Views:
    337
    Phillip Vong
    Apr 6, 2007
  4. Neal Becker

    buffer creates only read-only buffer?

    Neal Becker, Jan 8, 2009, in forum: Python
    Replies:
    0
    Views:
    419
    Neal Becker
    Jan 8, 2009
  5. Greg Ercolano
    Replies:
    5
    Views:
    308
    Greg Ercolano
    Mar 6, 2006
Loading...

Share This Page