Why is the windows return code called HRESULT? - c

The standard return type for functions in Windows C/C++ APIs is called HRESULT.
What does the H mean?

Result handle as stated here at MSDN Error Handling in COM

The documentation only says:
The return value of COM functions and methods is an HRESULT, which is not a handle to an object, but is a 32-bit value with several fields encoded in a single 32-bit ULONG variable.
Which seems to indicate that it stands for "handle", but is misused in this case.

Hex Result.
HRESULT are listed in the form of 0x80070005. They are a number that gets returned by COM\OLE calls to indicate various types of SUCCESS or FAILURE. The code itself is comprised of a bit field structure for those that want to delve into the details.
Details of the bit field structure can be found here at Microsoft Dev Center's topic Structure of COM Error Codes and here at MSDN HRESULT Structure.

The H-prefix in Windows data types generally designates handle types1 (such as HBRUSH or HWND). The documentation seems to be in agreement, sort of:
The HRESULT (for result handle) is a way of returning success, warning, and error values. HRESULTs are really not handles to anything; they are only values with several fields encoded in the value.
In other words: Result handles are really not handles to anything. Clearly, things cannot possibly have been designed to be this confusing. There must be something else going on here.
Luckily, historian Raymond Chen is incessantly conserving this kind of knowledge. In the entry aptly titled Why does HRESULT begin with H when it’s not a handle to anything? he writes:
As I understand it, in the old days it really was a handle to an object that contained rich error information. For example, if the error was a cascade error, it had a link to the previous error. From the result handle, you could extract the full history of the error, from its origination, through all the functions that propagated or transformed it, until it finally reached you.
The document concludes with the following:
The COM team decided that the cost/benefit simply wasn’t worth it, so the HRESULT turned into a simple number. But the name stuck.
In summary: HRESULT values used to be handle types, but aren't handle types any more. The entire information is now encoded in the value itself.
Bonus reading:
Handle types losing their reference semantics over time is not without precedent. What is the difference between HINSTANCE and HMODULE? covers another prominent example.
1 Handle types store values where the actual value isn't meaningful by itself; it serves as a reference to other data that's private to the implementation.

Related

How to filter CM_Get_Device_Interface_List with GUID_DEVINTERFACE_DISK?

How can I call CM_Get_Device_Interface_List for GUID_DEVINTERFACE_DISK type devices only? There was a similar question, and the questioner's code is just type-casting it like:
LPGUID InterfaceClassGuid = (LPGUID)&GUID_DEVINTERFACE_MODEM;
CM_Get_Device_Interface_ListW(InterfaceClassGuid, NULL, DeviceList, DeviceListLength, CM_GET_DEVICE_INTERFACE_LIST_PRESENT);
This seems unlikely to work, and when I tried it, it gave me: argument of type "LPGUID" is incompatible with parameter of type "PCWSTR". The first parameter of CM_Get_Device_Interface_List is type PCWSTR (a string), so I do not think GUID can be typecast to a string.
I have searched the web for "GUID_DEVINTERFACE_DISK" and "CM_Get_Device_ID_List", and there were almost no result but this Japanese blog. The page does not show any code, but just had a paragraph describing the overall procedure. It says:
Pass GUID_DEVINTERFACE_DISK to SetupDiGetClassDevs() to get the list of physical disks, and using SetupDiEnumDeviceInfo() for each disk, pass the disk's DEVINST to the CM_Get_Device_ID_List function with the flag of CM_GETIDLIST_FILTER_REMOVALRELATIONS, you can get the list of the volume names on the disk.
I have tried calling SetupDiGetClassDevs and SetupDiEnumDeviceInfo, and the DEVINST values were just 1 and 2 (I have two disks on the computer). It does not seem like I could filter CM_Get_Device_Interface_List with "1" and "2".
Damn, this is so very complicated and searching Google gives me few examples.

AVFrame deprecated attributes to regain?

I want to print out some attributes of video frames: I've looked into AVFrame struct, but only found the following disappointments:
attribute_deprecated short * dct_coeff
attribute_deprecated uint32_t * mb_type
It seems to me everything I am interested in is already obsolete. Btw, I didn't find
int16_t(*[2] motion_val )[2]
attribute in the actual frame I captured. My question is: how can i get access to those attributes such as dct_coeff or motion_vector or mb_type of a frame at all?
See av_frame_get_side_data(frame,AV_FRAME_DATA_MOTION_VECTORS) for the motion vectors. The other two have no replacement. The documentation states that they're mpeg-specific and using internal implementation details, which is why no replacement was provided.
(Don't forget to set avctx->flags2 & AV_CODEC_FLAG2_EXPORT_MVS, otherwise it's not exported.)
For the two with no replacement, I understand you might want that type of information if you're e.g. writing a stream analyzer, but FFmpeg really doesn't provide a stream-analyzer-level API right now. They could - if there's a more generic API - obviously be added as a separate side-data type. If you want that, you should probably become a FFmpeg developer and work on a broader API that is not MPEG-specific (e.g. does not use internal macros for mb_type), possibly even implement it for other codecs. In any other case, I don't really see why you would want that information. Can you elaborate?

How to avoid collision of enumerated values?

I'm building a front-end library. The back-end produces a number of error codes that are enumerated:
enum backerr {BACK_ERR1, BACK_ERR2, BACK_ERR3};
My front-end produces a number of additional error codes:
enum fronterr {FRONT_ERR1, FRONT_ERR2, FRONT_ERR3};
For convenience I would like to have a single error code returning function that would return both front end or back end errors depending on which one occurred.
Is there any way this can happen without collision of the values of two error codes, and considering we cannot know the values of the back-end?
If you don't know what the back end may generate then, no, there is no way to reliably select your own error codes so that they don't clash.
So you have a couple of options (at least).
The first is useful if the back end somehow publishes the error ranges, such as in a header file. To be honest, it should be doing this since there's no other way for a program to distinguish the different error codes and/or types.
If they are published, it's a simple matter for you to discover the highest and select your own codes to leave plenty of room for the back end to expand. For example, if the back end uses 1..100, you start yours at 1000. The chance of any system suddenly reporting ten times as many errors as the previous version is a slim one.
A second way is if you want real separation with zero possibility of conflict.
There's nothing to stop you returning a structure similar to:
struct sFrontError {
enum fronterr errorCode;
enum backerr backendCode;
};
and using that for your errors. Then your enumeration for the front end becomes:
enum fronterr {FRONT_OK, FRONT_BACK, FRONT_ERR1, FRONT_ERR2, FRONT_ERR3};
and you can evaluate it as follows:
If errorCode is FRONT_OK, there is no error.
If errorCode is FRONT_BACK, the error came from the back end, and you can find its code in backendCode.
Otherwise, it's a front end error and the code in errorCode fully specifies it.
If the backend exposes an exhaustive list of its error codes you can easily create a true superset of them with your own frontend error codes being a disjoint subset.
/* in backend.h */
enum backend_error
{
BACK_ERR_1,
BACK_ERR_2,
BACK_ERR_3,
};
/* in frontend.h */
#include <backend.h>
enum frontend_error
{
FRONT_ERR_1 = BACK_ERR_1,
FRONT_ERR_2 = BACK_ERR_2,
FRONT_ERR_3 = BACK_ERR_3,
FRONT_ERR_4,
FRONT_ERR_5,
};
This method doesn't force you to make any assumptions on the values of the backend error codes but if a future version of the backend defines additional error codes, you might be hosed. Another downside is that your header file #includes the backend's header so you are polluting the namespace.
If your users never call into the backend directly, that is, you are providing abstractions for all backend functionality, you can define your own error codes altogether and have a function that maps backend error codes to your own. Since it is not required for this function to be the identity function, you can always make this work even in face of future changes to the backend. It can also be implemented in your own implementation file to keep the backend namespace out of your user's picture.

TCL/C - when is setFromAnyProc() called

I am creating a new TCL_ObjType and so I need to define the 4 functions, setFromAnyProc, updateStringProc, dupIntRepProc and freeIntRepProc. When it comes to test my code, I see something interesting/mystery.
In my testing code, when I do the following:
Tcl_GetString(p_New_Tcl_obj);
updateStringProc() for the new TCL object is called, I can see it in gdb, this is expected.
The weird thing is when I do the following testing code:
Tcl_SetStringObj(p_New_Tcl_obj, p_str, strlen(p_str));
I expect setFromAnyProc() is called, but it is not!
I am confused. Why it is not called?
The setFromAnyProc is not nearly as useful as you might think. It's role is to convert a value[*] from something with a populated bytes field into something with a populated bytes field and a valid internalRep and typePtr. It's called when something wants a generic conversion to a particular format, and is in particular the core of the Tcl_ConvertToType function. You probably won't have used that; Tcl itself certainly doesn't!
This is because it turns out that the point when you want to do the conversion is in a type-specific accessor or manipulator function (examples from Tcl's API include Tcl_GetIntFromObj and Tcl_ListObjAppendElement, which are respectively an accessor for the int type[**] and a manipulator for the list type). At that point, you're in code that has to know the full details of the internals of that specific type, so using a generic conversion is not really all that useful: you can do the conversion directly if necessary (or factor that out to a conversion function).
Tcl_SetStringObj works by throwing away the internal representation of your object (with the freeIntRepProc callback), disposing of the old bytes string representation (through Tcl_InvalidateStringRep, or rather its internal analog) and then installing the new bytes you've supplied.
I find that I can leave the setFromAnyProc field of a Tcl_ObjType set to NULL with no problems.
[*] The Tcl_Obj type is mis-named for historic reasons. It's a value. Tcl_Value was taken for something else that's now obsolete and virtually unused.
[**] Integers are actually represented by a cluster of internal types, depending on the number of bits required. You don't need to know the details if you're just using them, as the accessor functions completely hide the complexity.

Is it a bad idea to mix bool and ret codes

I have some programs which make heavy use of libraries with enumerations of error codes.
The kind where 0(first value of enum) is success and 1 is failure. In some cases I have my own helper functions that return bool indicating error, in other cases I bubble up the error enumeration. Unfortunately sometimes I mistake one for the other and things fail.
What would you recommend? Am I missing some warnings on gcc which would warn in these cases?
P.S. it feels weird to return an error code which is totally unrelated to my code, although I guess I could return -1 or some other invalid value.
Is it a bad idea? No, you should do what makes sense rather than following some abstract rule (the likes of which almost never cater for all situations you're going to encounter anyway).
One way I avoid troubles is to ensure that all boolean-returning function read like proper English, examples being isEmpty(), userFlaggedExit() or hasContent(). This is distinct from my normal verb-noun constructs like updateTables(), deleteAccount() or crashProgram().
For a function which returns a boolean indicating success or failure of a function which would normally follow that verb-noun construct, I tend to use something like deleteAccountWorked() or successfulTableUpdate().
In all those boolean-returning cases, I can construct an easily readable if statement:
if (isEmpty (list)) ...
if (deleteAccountWorked (user)) ...
And so on.
For non-boolean-returning functions, I still follow the convention that 0 is okay and all other values are errors of some sort. The use of intelligent function names usually means it's obvious as to which is which.
But keep in mind, that's my solution. It may or may not work for other people.
In the parts of the application that you control, and the parts that make up your external API I would say, choose one type of error handling and stick to it. Which type is less important, but be consistent. Otherwise people working on your code will not know what to expect and even you yourself will scratch you head when you get back to the code in a year or so ;)
If standardizing on a zero == error scheme, you can mix and match both enum and bool if you construct your tests like this:
err = some_func();
if !err...
Since the first enum evaluates to zero and also the success case it matches perfectly with bool error returns.
However, in general it is better to return an int (or enum) since this allows for the expansion of the error codes returned without modification of calling code.
I wouldn't say, that it's a bad practice.
There's no need to create tons of enum-s, if you just need to return true/false, and you don't have other options (and true and false are explanatory enough ).
Also, if your functions are named OK, you will have less "mistakes"
For example - IsBlaBla - expects to return true. If you have [Do|On]Reload, a reload could fail for many reasons, so enum would be expected. The same for IsConnected and Connect, etc.
IMHO function naming helps here.
E.g. for functions that return a boolean value, is_foo_bar(...), or for functions that return success or an error code, do_foo_bar(...).

Resources