+HCU papers
courtesy of reverser's page of reverse engineering
05 June 1998
SLH's fifth paper
The Eye Of The Warrior

"There is no reason in terms of code generation why these RAD systems are so bloated in their output except that they include a mountain of dead code that is not used by the application. This is sloppy programming from people who not only should know better but also charge like wounded bulls for the "privelege" of manipulating this PUKE"

SLH is back again with another (the fifth) of his small masterpieces: You would be well advised to read all the preceding parts of what is going to be a DEFINITIVE HCU MANUAL INTRODUCING WINDOWS DISASSEMBLING: it's a concentrated very good course about the UTMOST IMPORTANCE of assembling in everyday windows (or whatever) programming. This will help you, among other things :-) in order to better understand the purposes (and the power) of what we are all doing here...

08 May 98 SLH ~ hutch1.htm The supression and resurrection of assembler programming. papers ~fra_0116
16 May 98 SLH ~ hutch_61.htm The Bridge: In Pursuit Of Lost Knowledge papers ~fra_011C
21 May 98 SLH ~ hutquest.htm THE QUEST: Building the launch pad papers ~fra_011F
29 May 98 SLH ~ hutch28.htm Software warriors through the warp papers ~fra_0123

And here you go... Enjoy!

+HCU papers
> The Eye Of The Warrior
> Depending on the story you read, Excalibur was handed to King Arthur by the
> Lady of the Lake to continue the quest of re-uniting his country, a task
> that his father had failed to achieve. Modern software warriors will have to
> do more than expect that their sword will be given to them.
> Sword making is one of the ancient arts based on the necessity of doing
> battle with a reliable weapon that would not break under the most severe
> conditions. In mediaeval Japan, the art of making the "Katana", the famous
> weapon of the Samurai, produced blades of considerable excellence seven
> hundred years before steel became commonly available through the Bessemer
> process.
> The skills involved were complex and difficult, forging, hardening,
> tempering, grinding, polishing through to the condition where the warrior
> had a weapon of excellence that would serve him through the tribulations of
> his profession.
> The modern software warrior must produce software that is sharp edged,
> flexible, light and well balanced to met the challenge that lays ahead.
> The "sword" offered by the RAD vendors has the appearance of greatness with
> a shiny blade, a beautifully engraved handle and an inlaid scabbard but when
> you pick it up it is too heavy (bloat), try to do combat with it and the
> blade gaps and snaps (GP faults), and when you try to fix it, the basic
> material is not good enough to repair.
> The programmers who has undertaken the quest to recover lost knowledge will
> have their API template hardened and tempered like the swords of legend,
> with the mastery of using the normal controls, menus and resources, the
> handle will be well shaped and securely attached, the next thing is to
> refine its appearance and sharpen the blade.
> The swordsmith at work.
> ~~~~~~~~~~~~~~~~~~~~~~
> One of the most irksome aspects of windows GUI programming is the percentage
> of development time spent designing the interface so that a programs user
> can interact with it in a convenient and predictable way. One of the curses
> of some of the old style DOS software was that the user needed to attend a
> course to learn how to interact with the program.
> One of the few things Microsoft got right was the standardisation of some
> of the interface characteristics so that the user did not have to start from
> scratch each time they started up a different program. The problem is that
> the extension of this standardisation became a straight jacket to the
> developer.
> A casual glance through some of the software currently on the market says
> much about the environment it was developed in, the proliferation of
> dockable toolbars says Microsoft visual C++, the endless manipulation of
> icons and font listings says one of the versions of visual basic, dialog
> boxes and buttons from BWCC & BWCC32 DLLs reveal Borland origin yet the
> programmer who masters the lower level functions in the API does not have
> to wear the straight jacket imposed by the corporate vendors.
> Interface design, when freed from the gimmicks, has a very useful function
> in making the software easier to understand and use and there are a number
> of ways of getting the majority of desired characteristics without either
> the bloat or the gimmicks.
> To fuel the glitzy front end of Win Doze 95, Microsoft sneaked in a couple
> of new styles for buttons where you can either use bitmaps or icons as the
> button's image. This considerably simplifies bitmap buttons from the days
> when owner draw buttons were the only way of getting an image onto a button.
> Icons are easier to use because of the routine capacity to include
> transparent backgrounds in the image which means that they do not interfere
> with the background colour of the button but they come in less than useful
> square shapes and set sizes.
> Bitmaps have the advantage of being able to be loaded at any size and shape
> but it comes with a catch, images saved as bitmaps hard code the background
> colours into the file which will clash with a different colour set by the
> user in their 3Dobject option. Fortunately, there is a solution to the
> problem that only takes a little coding to solve.
> Write a function that creates a button that has the additional BS_BITMAP
> included something like as follows.
>     FUNCTION = CreateWindow("BUTTON","", _
>                             WS_VISIBLE or WS_CHILD or BS_BITMAP, _
>                             x,y,wd,ht,hParent,ID,hInstance,0)
> The return value is the handle to the button. After you have created the
> bitmap and compiled it into your resource file, call your button function,
>     hBtn1 = BmpButton(5,5,55,25,hWnd,110)
> When you set the size of the button, make sure you allow a couple of pixels
> each side for the button's border. Then you load the bitmap from the
> resource file,
>     hBmp = LoadBitmap(hInstance,"MYBITMAP")
> To solve the problem of clashing background colour, a function has been
> included at the end of this document that reads the background colour of
> your bitmap and uses ExtFloodFill() to change it to the colour of the button
> face. You call it as follows,
>     hBmp = SetBmpColor(hBmp)
>   passing the handle of the resource bitmap and receiving back the same
> handle to the bitmap after it has been modified. All that needs to be done
> after this is to send the following message to the button,
>     SendMessage hBtn1,BM_SETIMAGE,0,hBmp
>   and you bitmap button is up and running with the correct background
> colour. This means that once you have the functions up and going, you do a
> bitmap button in four lines of code which is a damned site quicker than
> slopping a button onto a form and then ratting around to find the bitmap
> that you want to pour into it.
> This process works just as well on the strip bitmaps used in the toolbar
> controls. All you need to ensure is that the bitmap has a "path" for the
> floodfill function to access all of the background colour. One of those
> little secrets that nobody tells you is that PaintBrush is a leading edge
> toy for drawing toolbar and button bitmaps. Excellent for manipulating
> text for 3D shadow effects.
> An important thing when using resources is to delete them when finished.
> Somewhere in your exit code you make a corresponding call to,
>     DeleteObject hBmp
> A good habit to learn is when you allocate a resource, you also write the
> code to de-allocate it otherwise you application will leak like a sieve.
> While allocated bitmap resources are usually recovered when the program
> exits, using GDI function for screen display is critical in the recovery
> of brushes, pens and images, otherwise the resource waste can bring the
> application to a halt as the system runs out of GDI memory.
> This is the windows programmer's law of gravity, what goes up must come
> down, forget it and it will come down around your ears with a crash.
> Sharpening the blade
> ~~~~~~~~~~~~~~~~~~~~
> From the Italian Renaissance masters to the portrait painters of modern
> times, the difference between a flat and lifeless painting and a painting
> that revealed more than the subject often desired was the gradient of light
> to shadow.
> In a different and restricted way, the programmer needs to master the
> capacity that is available to give their software the illusion of dimension
> so that its user more easily comprehends the subtleties of the interface.
> Some of this has been made easier through the additional styles available
> in CreateWindowEx(). Include the WS_EX_CLIENTEDGE style in either the main
> window or a control and you have a consistent 3D border around the control
> or window.
> For more control laying out the interface, you write a function that is
> called by the WM_PAINT message in the WndProc message handling function. In
> designing this function, you would pass it both the window handle and the
> device context handle as both values are useful.
> There is a windows API called DrawEdge() that allows the programmer to do
> a wide range of lines and frames in the system colour and size anywhere in
> the client area of the application. This will extend the interface capacity
> but the function is not particularly fast or flexible.
> There is a better way that is based on the not so well kept secret that to
> provide the glitzy front end for win 95, Microsoft had to hard code a lot of
> the GDI in assembler. There are a complimentary pair of functions called
> respectively MoveToEx() and LineTo() that when used with a single pixel wide
> pen, are genuinely fast.
> There are two functions at the end of this document that use these two APIs
> to draw lines and frames and they have the advantage that if you provide the
> device context, they will draw on anything. They are respectively,
>     DrawLine() and Frame3D().
> These two functions have passed the test of time in that they were
> originally written in 16 bit windows C and were fast enough then to provide
> the framing and other line drawing for 3D layouts when there was no other
> choice.
> In 32 bit windows, they provide considerable power and flexibility to draw
> frames around groups of controls, frames around windows that adjust
> dynamically when the window is resized, or in fact, anything you like.
> To use them efficiently, you need to provide the dimensions for the frames
> and it is here where a couple of the information retrieval functions are
> very useful. Using a RECT structure / Data Type and filling it with the
> GetClientRect() gives you the width and height of the client area which you
> then use to provide the dimensions for the frames around the client area.
> Retrieving the dimensions of a control in the client area involves using
> two functions, GetWindowRect() will give you the dimensions in absolute
> screen co-ordinates, then you use ScreenToClient() to convert the top left
> co-ordinate to a client area position. In C you use a POINT structure to
> convert this information, in basic you use a POINTL data type.
> Once you have the dimensions of the area you wish to frame, the Frame3D()
> function was written so that the four co-ordinates could be incremented or
> decremented to easily step successive frames.
> Work out how far you want the frame from the controls in pixels and then
> subtract that value from the top x and top y co-ordinates and add that
> value to the lower x and lower y co-ordinate.
> Call this value "Step".
>     LOCAL Step as LONG
>     LOCAL hi   as LONG
>     LOCAL lo   as LONG
>     hi=GetSysColor(COLOR_3DHIGHLIGHT)
>     lo=GetSysColor(COLOR_3DSHADOW)
>     Step = 5
>     Void = Frame3D(hDC,hi,lo,tx-Step,ty-Step,lx+Step,ly+Step,1)
> To make the next frame, you simply copy the proceeding two lines of code,
> reverse the two colour parameters and increment the step parameter.
>     Step = 8
>     Void = Frame3D(hDC,lo,hi,tx-Step,ty-Step,lx+Step,ly+Step,1)
> Inlining the function calls this way is the fastest way to do it and the
> overhead is trivial.
> Juggling the border width parameter allows you to give the illusion of
> height change so that you can provide a "sculptured" appearance in the areas
> that you wish to highlight. Overdo it and your interface can look like a
> cluttered mess but get it right and you have busted out of the straight
> jacket that Microsoft have implemented in win 95.
> This technique called from the WM_PAINT message gives you persistent objects
> for the price of a few function calls which are like lightning instead of
> having to load some junkheap DLL to get a control to do the same thing.
> Decorating the handle
> ~~~~~~~~~~~~~~~~~~~~~
> Some image data is too complex to generate any other way than the use of
> bitmaps that are usually drawn externally in image editors. You would
> normally expect that a GUI based operating system would have a function that
> would display an image where you wanted it but it just does not exist, you
> have to write the code to display an image using low level functions out of
> the GDI.
> At low level, the process is not all that difficult, as long as you
> understand what the mechanics of the technique are. If you wish to display
> a bitmap on part of the client area, first you get the device context with
> the function call GetDC(hWnd). Then you create a memory device context using
>     mDC=CreateCompatibleDC(NULL)
>   select your bitmap into that memory device context using the following,
>     hOldBmp=SelectObject(mDC,hBitmap)
> and you can do almost anything you like with it. You can use GDI functions
> to either modify it or draw on it and then when you have done the processing
> that you want, you "blit" it onto the client area at whatever location you
> want. For size for size "blitting" you use BitBlt() - Bit Blit, and for size
> change up or down you use StretchBlt() - Stretch Blit.
> The last parameter in both functions give you a range of very useful options
> for the method in which you display the image.
> Conceptually, the idea of creating a memory device context is something like
> creating an invisible piece of screen that you can load images onto and use
> GDI functions to draw on. The "blit" functions are fast enough to use this
> technique for animation which is generally how it is done.
> If you want an image to be a persistent object, simply call the code to
> display it from you function that is called from the WM_PAINT message and
> it will remain visible after other windows have overlapped it or your own
> window has been minimised or maximised.
> This is particularly useful if you wish to display a logo on part of the
> client area. It is easy to frame your logo using the framing function
> supplied and you do not need a control to do it.
> One of the sobering facts that you will face is that even a moderate use of
> bitmap data will use more disk and memory space than the functions used to
> manipulate them at low level but this is part of the price you pay for
> working in a graphical environment.
> The difference is that by writing your code at low level, you have not
> produced the bloat that is associated with RAD front ends and you have near
> absolute control over the layout and appearance of your interface.
> With the mastery of interface layout and design, the low level programmer
> is very close to where the action is, a mimimum size window and messaging
> footprint, the range of standard controls that can be pelted around at
> rates that scare the uninitiated and finally the nearly unlimited control
> of the appearance of the interface.
> What the low level programmer is doing is much the same as the RAD system
> designer in packaging groups of low level functions together as larger high
> level functions, the difference is that instead of producing a big, slow,
> sloppy compromise with its restrictions, leaks and bugs, the low level
> programmer selects exactly what is needed and no more which accounts for
> the dramatic difference in size.
> This is related to a well known problem in static library design, a problem
> called granularity. If you write each low level function as a seperate
> module, it takes a bit more work and you risk carrying a little more
> overhead in the function calls but on the other end, if a large number of
> functions are included in the same module, when you call one, you get the
> code for the rest as well.
> At its worst, it means that if you call a function that may only have a
> couple of hundred bytes in it, you get a mountain of junk attached to it
> which is not used by your program. This is something like an olympic runner
> competing with an anvil tied around their neck.
> There is no reason in terms of code generation why these RAD systems are so
> bloated in their output except that they include a mountain of dead code
> that is not used by the application. This is sloppy programming from people
> who not only should know better but also charge like wounded bulls for the
> "privelege" of manipulating this PUKE.
> An apt term for this stuff is "Maggot ware", the bugs have been in it for so
> long that you can see the maggots crawling around in it.
> The eye
> ~~~~~~~
> The eye of the ancient warriors is like the weapons that they crafted of
> old, an eye that penetrates like cold steel. It looks at the compile size,
> watches the execution speed, notes the interface layout and whether the
> design is clear and easy to use.
> As you undertake the quest for lost knowledge you will feel the eye of the
> ancient warriors looking over your shoulder and you will know whether they
> approve or disapprove of your coding for as you undertake the quest, your
> eye will become as their eye and you will see and comprehend as they do.
> Some of the ancient warriors have seen many things and used many tools and
> toys in their time but the fundamental logic of software design is nearly
> eternal in that much of what was learnt of old is useful in a new and
> different age where there are challenges that did not exist in the past.
> If Fortran was like Little Richard's "Lucille", Cobol was like the strained
> refrains of "Leader of the Pack", Pascal was listening to a chamber
> orchestra playing Telemann with the necessary clipped precision, C was
> cruising the freeway in your Caddillac playing Led Zepperlin cassettes,
> (before CDs), tons of hoot but lousy around tight corners, Basic was pure
> bubble gum music for the kiddies and Assembler was a Disco at 3AM with the
> Cerwin Vega bass bins growling Metallica with enough grunt to make your head
> bang.
> With modern RAD, you just have MUSAK, a pale and limpid imitation of the
> real thing, soda pop when all you need is a scotch, spam instead of ham,
> Mantovani when you just wanna Rock an' Roll, a concept in its execution
> that is as phony as a three dollar bill but you'll pay heaps more for it.
> With no deference to the pioneers who had their code generated on punch
> cards, Cobol and Fortran are nearly finished although some of the "old
> fellas" with a background in Fortran can routinely rip apart the stress
> calculations for city building out of their gigabytes of punch card written
> routines in the time it would take many to try and get a handle on the
> problem.
> Pascal is in trouble with only one vendor supporting it where the startup
> code is encapsulated into the RAD generator but it will still deliver
> grunty DLLs.
> C will probably survive because of its sheer power and user base but where
> C++ should be its successor, it is currently being nobbled by the packages
> that it comes in.
> Basic is like the Phoenix, just when you think it is dead, someone writes a
> new version of Basic as it has a wide user base that likes writing software
> that way, bubble gum and all. The viability of the Power Basic compiler
> comes from it being written to produce DLLs which just can't be done in the
> toothless terror that Visual Basic has remained.
> Of all the languages, assembler will be with us for a long time because
> the processors of the future will have their own native language and this
> is where the action will be.
> For those ancient warriors who have yet to contribute, the situation is
> much like the story of King Arthur. As he lay dying, he ordered his knight
> Sir Bedivere to cast Excalibur back into the lake from where the lady of
> the lake had passed it to him many years before.
> Sir Bedivere's misplaced value on Excalibur led him to hide it a number of
> times but when Arthur finally commanded him to do as he ordered, Bedivere
> took it back to the lake and in the moonlight, cast it high over the lake.
> As it fell near the surface of the water, the hand that passed it to Arthur
> so long ago rose out of the water and caught Excalibur by the hilt,
> brandished it three times and disappeared below the surface of the water.
> For the knowledge that you have, there must be no Sir Bedivere, returning
> your knowledge back into the lake is no more than posting it on the
> Internet. You may never see the arm that brandishes it but if it is clear
> and well written, it will grow in the fertile minds of the new generation of
> software warriors.
> The gauntlet
> ~~~~~~~~~~~~
> Here is the challenge for those ancient warriors who are still doing battle
> as corporate insiders, as Daniel of old could read the writing that was on
> the wall for the Babylonian kingdom, you too must be able to read the
> writing on the wall for the current empires that are destroying the fabric
> of the computer industry and the people who depend on it through illegal
> monopolistic practices.
> Make your contribution to the future of the industry by revealing the hidden
> knowledge that you have at hand for it is only a matter of time until the
> Department of Justice action against Microsoft will start to bite and the
> empire as it is currently known will go the way of others who have continued
> to act as if they were above the law.
>  --------------------------------------------------------------------------
> The three functions below were converted from their C original into Basic so
> that they are easier to read for people of different language backgrounds.
> Converting them back to C is easy, as long as attention is paid to the
> correct data types.
> ' ########################################################################
> FUNCTION Frame3D(hDC as LONG, _
>                Colr1 as LONG, _
>                Colr2 as LONG, _
>                   tx as LONG, _
>                   ty as LONG, _
>                   lx as LONG, _
>                   ly as LONG, _
>                 bWid as LONG) as LONG
>     'Sources for the two colour parameters
>     '~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>     'hi&=GetSysColor(%COLOR_3DHIGHLIGHT)
>     'lo&=GetSysColor(%COLOR_3DSHADOW)
>     'tl&=GetNearestColor(hDC,RGB(127,127,127))
>     'lr&=GetNearestColor(hDC,RGB(255,255,255))
>     '-----------------------------------------
>     ' The calling function must pass the following parameters,
>     ' hDC, Device context handle,
>     ' Colr1 is the 1st rgb color
>     ' Colr2 is the 2nd rgb color
>     ' tx, top   x co-ordinate
>     ' ty, top   y co-ordinate
>     ' lx, lower x co-ordinate
>     ' ly, lower y co-ordinate
>     ' bWid, border width in pixels
>     LOCAL hOldPen as LONG
>     LOCAL hPen1   as LONG
>     LOCAL hPen2   as LONG
>     LOCAL ref     as LONG
>     hPen1=CreatePen(%PS_SOLID,1,Colr1)
>     hOldPen=SelectObject(hDC,hPen1)
>     '    tx         lx
>     ' ty  -----------
>     '    |           |
>     '    |           |
>     ' ly  -----------
>     ref = 0
>     do
>       MoveTo hDC, tx + ref, ty + ref
>       LineTo hDC, lx - ref, ty + ref
>       MoveTo hDC, tx + ref, ty + ref
>       LineTo hDC, tx + ref, ly - ref
>       ! inc ref
>     loop while ref < bWid
>     hPen2=CreatePen(%PS_SOLID,1,Colr2)
>     SelectObject hDC,hPen2
>     DeleteObject hPen1
>     '    tx         lx
>     ' ty  -----------
>     '    |           |
>     '    |           |
>     ' ly  -----------
>     ref = 0
>     do
>       MoveTo hDC, tx + ref, ly-1 - ref
>       LineTo hDC, lx - ref, ly-1 - ref
>       MoveTo hDC, lx-1 - ref, ty + 1 + ref
>       LineTo hDC, lx-1 - ref, ly - ref
>       ! inc ref
>     loop while ref < bWid
>     SelectObject hDC,hOldPen
>     DeleteObject hPen2
>     FUNCTION = 0
> '##########################################################################
> FUNCTION DrawLine(hDC as LONG, Colr as LONG, a&, b&, c&, d&) as LONG
>     ' Use either of the two following function calls to provide
>     ' the colour parameter for this function.
>     ' sColr=GetSysColor(COLOR_3DSHADOW)
>     ' gncol=GetNearestColor(hDC,RGB(127,127,127))
>     LOCAL hpen&
>     LOCAL hpenOld&
>       hPen&=CreatePen(%PS_SOLID,1,Colr)
>       hpenOld&=SelectObject(hDC,hpen&)
>         MoveToEx hDC,a&,b&,ByVal %NULL
>         LineTo hDC,c&,d&
>       SelectObject hDC,hpenOld&
>       DeleteObject hpen&
>     FUNCTION = 0
> '##########################################################################
> FUNCTION SetBmpColor(hBitmap&) as LONG
> ' Call function as follows to set bmp colour
> ' background to the system set %COLOR_BTNFACE
> '   hBitmap&=SetBmpColor(hBitmap&)
> '   ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
>     LOCAL mDC as LONG
>     mDC=CreateCompatibleDC(%NULL)
>     hOldBmp&=SelectObject(mDC,hBitmap&)
>     hBrush&=CreateSolidBrush(GetSysColor(%COLOR_BTNFACE))
>       hOldBrush&=SelectObject(mDC,hBrush&)
>         rv&=ExtFloodFill(mDC,1,1,GetPixel(mDC,1,1),%FLOODFILLSURFACE)
>       SelectObject mDC,hOldBrush&
>     DeleteObject hBrush&
>     hReturn&=SelectObject(mDC,hBitmap&)
>     DeleteDC mDC
>     FUNCTION = hReturn&
> ' ########################################################################


+HCU papers
redhomepage red links red anonymity red+ORC redstudents' essays redacademy database
redantismut redtools redbots & agents reversing redcocktails redjavascript wars redsearch_forms redmail_reverser
redIs reverse engineering illegal?