0

I am trying to write some portable code and I've been thinking how did Microsoft implement old C runtime routines like gmtime or fopen, etc which were returning a pointer, opposite to todays gmtime_s or fopen_s which requires object to passed and are returning some errno status code (I guess).

One way would be to create static (better than global) object inside such routines and return pointer to it, but if one object is currently using this static pointer and another object invokes that routine, first object would get changed buffer - which is not good.

Furthermore, I doubt that such routines uses dynamic memory because that would lead to memory leaks.

As with other Microsoft stuff, implementation is not opened so that I can take a peak. Any suggestions?

Milos Ljumovic
  • 403
  • 4
  • 16
  • Why would you need static objects? Why would dynamic memory cause memory leaks? – Thomas Padron-McCarthy Dec 07 '15 at 12:19
  • 1
    If I remember correctly, most parts of the MS C runtime source code *are* distributed with Visual Studio. – Martin R Dec 07 '15 at 12:21
  • You could stop guessing and [read the official reference](https://msdn.microsoft.com/en-us/library/z5hh6ee9.aspx). Or a [reference written from the specification](http://en.cppreference.com/w/c/io/fopen). – Some programmer dude Dec 07 '15 at 12:23
  • Also, it's not *that* unusual for some libraries to dynamically allocate memory on first call, and use that throughout the lifetime of the program. Unless it adds an `atexit` handler to free the memory it's technically a leak, but it's not a continuous leak and most modern operating systems will free that memory on termination anyway. – Some programmer dude Dec 07 '15 at 12:27

3 Answers3

1

Regarding gmtime, you are correct; it could have operated upon a variable that has static storage duration (which is the same storage duration as variables declared "globally", btw... There is no "global" in C). Historically speaking, you should probably assume this is the case, because C doesn't require that there be any support for multithreading. If you're referring to an era where there was decent support for multithreading, it's probable that gmtime might return something that has thread specific storage duration, instead, as the MSDN documentation for gmtime says gmtime and other similar functions "... all use one common tm structure per thread for the conversion."

However, fopen is a function that creates resources, and as a result it's reasonable to expect that every return value will be unique (unless it's an erroneous return value).

Indeed, fopen does constitute dynamic management; you are expected to call fclose to close the FILE once you're done with it... If you forget to close a file every now and then, there is no need to panic, as the C standard requires that the program close all FILEs that are still open upon program termination. This implies that the program keeps track of all of your FILEs behind the scenes.

However, it would obviously be a bad practice to repeatedly leak file descriptors, over and over again, constantly, for a long period of time.

autistic
  • 1
  • 3
  • 35
  • 80
  • What about smart pointers usage? We could implement such routine that could use smart pointer for resulting object. System should destroy such memory after usage, and we would still have routine which does return the pointer. I just don't know about (potential) system overhead, when dealing with this smart pointers. – Milos Ljumovic Dec 07 '15 at 12:44
  • @MilošLjumović Are you referring to the "smart pointers" that C++ has, in a question that has nothing to do with C++? – autistic Dec 07 '15 at 12:52
  • Don't mind, but yes. As I said I am thinking about correct approach. Question was related to C run-time in order for me to understand the concept behind it. – Milos Ljumovic Dec 07 '15 at 13:01
  • 1
    @MilošLjumović It is possible for runtime to detect memory leaks of any kind and clean up after them. This is demonstrated by garbage collection in programming languages such as Javascript, C# and Java. Sure, a C implementation could implement `malloc` (or `gmtime`) on top of a GC with `free` (no destructor corresponding to `gmtime`) as a hint for the GC... The problem is that there's virtually no benefit (due to projects such as valgrind that allow us to detect memory leaks) for the (rather extreme) overhead. – autistic Dec 07 '15 at 13:22
  • 1
    @MilošLjumović In fact, it's possible to statically detect memory leaks... You probably wouldn't want to use a compiler that performs such heavy analysis, though... – autistic Dec 07 '15 at 13:24
1

Well, first, such globals and statics cannot be used anyway because of thread-safety.

The use of dynamic memory, or arrays, or arrays of handles, or other such combos DO leak resources if the programmer misuses them. On non-trivial OS, such resources are linked to the process and are released upon process termination, so it is a serious problem for the app, but not for the OS.

Martin James
  • 24,453
  • 3
  • 36
  • 60
0

I'm not sure about the Visual Studio specifics, but these function libraries are typically implemented as opaque type. Which is why they return a pointer and why you can't know the contents of the FILE struct.

Meaning there will either be a static memory pool or a call to malloc inside the function. There are no guarantees of the C library functions are re-entrant.

Calling fopen without having a corresponding fclose might indeed create a memory leak: at any rate you have a "resource leak". Therefore, make sure that you always call fclose.

As for the implementation details: you can't have the Visual Studio source code, but you could download

Lundin
  • 195,001
  • 40
  • 254
  • 396