-
Apr 19th, 2021, 03:57 AM
#1
This forum is why VB6 is still usable today
I just wanted to put it into words and say this - that this forum is one of the reasons why VB6 is still usable today. Twenty or more years of explained code, resources of all kinds, the code bank and the summed experiences of hundreds of programmers who have posted here and still do so on a regular basis, still providing targetted help on a daily basis.
It is so impressive that a forum with this level of vigour still exists so long after the main developer of the product exited the market.
When I post a request for help on a 20 year-old product I generally receive exactly the help I need within a day bearing in mind the timezone delays, the response is generally almost immediate.
It is impressive that such a community exists, it is the backbone of this site, and I somehow doubt the other sections (.NET, ASP, VBA) being not quite tributaries but certainly existing here because of VB6, wouldn't even be here if the VB6 section wasn't still thriving as it does.
We have to give MS some credit for creating such a useful tool, pitched so accurately at the market and targetted so well as a RAD tool for the masses, still used by them in its other direct incarnations, VBA and VBscript and also used by the world in that less VB6-derived product, in the guise of that non-basic but thoroughly .NET product - VB.FRED.
We VB6-ers are often Microsoft haters in that the companies' later products and more recent design methodologies have taken a turn for the worse but the fact that this part of the forum won't die is a testament to one of Microsoft's most rock solid products that it ever made.
VB6 has been criticised massively over the years but what they criticise (who are 'they' anyway?) has probably been the reason that VB6 survives in the third decade of the 21st century.
I just wanted to say how impressed I am that posts on this forum receive the amount of responses that they do. I could list those that regularly help me but I won't as I'd be bound to leave someone important out.
I have been having a discussion with a .NET programmer of many years experience and he sees me programming in VB6 and working with APIs to do this and that and he initially asked why I persisted in coding in a twenty-year old language that had fossilised in time and could not do the things later languages can do.
I explained that I am intending to contribute to ReactOS and precisely because VB6 cannot do the things later languages can do, learning how to replicate that functionality in code, gives me a lot of knowledge learning how APIs function and how Windows and therefore ReactOS does what it does.
C++ and C are not easy languages to use to learn these aspects but VB6 is the perfect tool for what I am doing. An accessible language used to learn about these aspects of the operating system using a strongly typed language to implement o/s type functions. There is some similarity to the use of C type languages in what I am doing.
I may yet be some way from contributing code to ReactOS yet but I am getting there. My code and understanding are improving.
I couldn't do any of this without this forum.
-
Apr 19th, 2021, 06:25 AM
#2
Re: This forum is why VB6 is still usable today
In a similar way, only decades earlier, you can still find active help for MVS\COBOL at https://www.mvsforums.com/. Some languages just keep on ticking.
Please remember next time...elections matter!
-
Apr 19th, 2021, 08:31 AM
#3
Re: This forum is why VB6 is still usable today
I actually love that its a fossilized language. I can open up a 20yr old project and not have to worry which version of the IDE and runtime I need in order to compile it.
Stable language with enough capabilities we can build whatever more we want and the hipsters with a fetish for new language features of the day leave us alone. Win Win
Last edited by dz32; Apr 19th, 2021 at 10:58 AM.
-
Apr 19th, 2021, 09:20 AM
#4
Re: This forum is why VB6 is still usable today
There's something to be said for stable, static, languages.
Of course, yereverluvinuncleber is intending to bolt a brass steam boiler onto ReactOS, but hey, whatever works....
My usual boring signature: Nothing
-
Apr 19th, 2021, 10:59 AM
#5
Re: This forum is why VB6 is still usable today
Originally Posted by Shaggy Hiker
Of course, yereverluvinuncleber is intending to bolt a brass steam boiler onto ReactOS, but hey, whatever works....
Now why do you say that? https://reactos.org/forum/viewtopic.php?t=15837
-
Apr 19th, 2021, 11:44 AM
#6
Re: This forum is why VB6 is still usable today
Many compiled high level languages are faring poorly. Read Why Do People Leave Xojo?
-
Apr 19th, 2021, 12:40 PM
#7
Re: This forum is why VB6 is still usable today
Originally Posted by yereverluvinuncleber
Because of that link. I hadn't seen it, I just knew that it had to exist if you were involved.
My usual boring signature: Nothing
-
Apr 19th, 2021, 12:45 PM
#8
Re: This forum is why VB6 is still usable today
Originally Posted by dilettante
That articles sums up why I'm skeptical of the VB6 replacement ideas like RADBasic and Twin Basic. They seem likely to founder on the same reef.
My usual boring signature: Nothing
-
Apr 19th, 2021, 07:17 PM
#9
Re: This forum is why VB6 is still usable today
Originally Posted by dz32
I actually love that its a fossilized language. I can open up a 20yr old project and not have to worry which version of the IDE and runtime I need in order to compile it.
won a like
-
Apr 20th, 2021, 12:40 AM
#10
New Member
Re: This forum is why VB6 is still usable today
for Microsoft,profit may be the best explanation for the abandonment of vb6.For customers, meeting their needs conveniently and quickly is the reason why vb6 is unforgettable for a long time.
-
Apr 23rd, 2021, 12:49 PM
#11
Re: This forum is why VB6 is still usable today
Originally Posted by Shaggy Hiker
That articles sums up why I'm skeptical of the VB6 replacement ideas like RADBasic and Twin Basic. They seem likely to founder on the same reef.
I'm cautious too, I've seen far too many "replacements" fail to deliver. But I have to say how impressed I am with the twinBasic early preview.
twinBASIC aims for 100% backwards compatibility with existing VB6 and VBA projects, plus 64 bit Windows compilation and Mac, Linux and Android compilation planned.
twinBASIC uses the VS Code IDE.
The language is very VB6-compatible with some extensions (many of which will be familiar to VB.Net users).
The preview compiles to unoptimized native code.
In the preview you can paste existing VB6 code and see it run in twinBASIC.
After the developers have fixed any issues in the preview, the following will be added:
- Forms / GUI support, including full backwards compatibility with existing VB6 forms.
- Native compilation, using the LVVM optimising compiler.
- Cross-platform compilation (Mac, Linux and Android).
twinBASIC was demonstrated today twinBASIC at the Access DevCon 2021 in Vienna, Austria.
https://www.vbforums.com/showthread....0181-TwinBasic
-
Apr 23rd, 2021, 01:06 PM
#12
Re: This forum is why VB6 is still usable today
If TwinBasic can deliver... It just might stand a chance...
Being 100% Vb6 compatible seems a bit incongruous with these claims (from their main page):
Return syntax is supported (as per VB.NET), using this disallows the old GoSub syntax
Per-procedure Handles/Implements event syntax as per VB.NET
Unless there's a way to flip back and forth, like through compatibility settings or directives.
If they can get a Linux version off the ground... I'd certainly entertain the possibility.
-tg
-
Apr 23rd, 2021, 03:39 PM
#13
Re: This forum is why VB6 is still usable today
Originally Posted by techgnome
Unless there's a way to flip back and forth, like through compatibility settings or directives.
-tg
In the first preview Gosub is disabled though apparently it is to return (no pun intended).
I don't know if there will be a way to switch it off, or if you just won't be able to use both in the same procedure.
Either way, no one should be using Gosub in VB6.
-
Apr 23rd, 2021, 03:49 PM
#14
Re: This forum is why VB6 is still usable today
Well, let's not let this thread get too sidetracked by one sole version of the competition to replace VB6. TwinBasic is making progress but RADBasic is making progress too. My hopes were for a community-driven effort to recreate VB6 - component by component but this group of highly competent programmers would rather fight each other viciously rather than agree to sit down to recreate what VB6 does so well.
It seems we have to leave it to virtual outsiders to come up with real solutions (Olaf's contributions excluded).
Apologies for the above, I just don't want this thread to be hijacked by the lovely idea of TwinBasic, we need to be equinanimous if that's a real word. I don't think it is.
I struggle with this forum, so positive in so many respects, such a wealth of skills in a small group of blokes (primarily men for certain) it is sad that they could not get their own act together to focus all that knowledge and create that VB6 replacement themselves.
Last edited by yereverluvinuncleber; Apr 23rd, 2021 at 03:52 PM.
-
Apr 23rd, 2021, 03:57 PM
#15
Re: This forum is why VB6 is still usable today
Originally Posted by VB6 Programming
Either way, no one should be using Gosub in VB6.
Like a lot of lore this isn't true. GoSub should be avoided nearly as much as DoEvents() calls, but it still has a valid place. Write enough code and you'll find out why.
The essential problem is that VB never offered nested procedures and data scopes any other way. To avoid GoSub when a procedure needs to do something multiple times you must either repeat all of that code several times inline or else write a separate procedure passing arguments that might get bulky, adding painful overhead.
GoSub is far from ideal, but it has a place.
-
Apr 23rd, 2021, 04:08 PM
#16
Re: This forum is why VB6 is still usable today
Originally Posted by dilettante
The essential problem is that VB never offered nested procedures and data scopes any other way.
Removing GoSub probably means twinBasic has some clever ideas to borrow from Pascal/Delphi about nested procedures, who knows. . . :-))
cheers,
</wqw>
-
Apr 23rd, 2021, 05:14 PM
#17
Re: This forum is why VB6 is still usable today
Originally Posted by wqweto
Removing GoSub probably means twinBasic has...
Gosub is only temporarily out of TwinBasic in this early preview. It will be brought back. But you won't be able to use it and also use the new Return syntax at the same time.
-
Apr 23rd, 2021, 05:47 PM
#18
Re: This forum is why VB6 is still usable today
Originally Posted by dilettante
...passing arguments that might get bulky, adding painful overhead.
GoSub is far from ideal, but it has a place.
It probably would (have a place), if there wasn't a huge performance-penalty...
Against all logic, Gosub is about factor 10-15 slower when native compiled
(compared with calling normal sub-routines with a handful of arguments).
Code:
Option Explicit
Private Sub Form_Click()
Cls
Dim result As Single, i As Long, a As Single, b As Single, T!
T = Timer
For i = 1 To 10 ^ 7
GoSub Calculate1
Next
Print "Gosub:", CLng((Timer - T) * 1000); "msec", result
result = 0: a = 0: b = 0
T = Timer
For i = 1 To 10 ^ 7
Calculate2 result, i, a, b
Next
Print "Subroutine:", CLng((Timer - T) * 1000); "msec", result
Exit Sub
Calculate1:
a = b / i: b = result + 1
result = a - b
Return
End Sub
Private Sub Calculate2(result As Single, i As Long, a As Single, b As Single)
a = b / i: b = result + 1
result = a - b
End Sub
The above produces (native compiled, all extended options):
- Gosub -> 620msec
- normal Sub -> 40msec
Olaf
-
Apr 23rd, 2021, 11:14 PM
#19
Re: This forum is why VB6 is still usable today
So when I was a kid, I hung out on AOL. In the chatrooms, there were all these chat games people were running, and of course warez servers and punters (sent people a specially crafted instant message that crashed their client)... so I looked at where people were getting such things, then in short order how to modify them. I learned backwards, performing more and more complex changes, until I could write my own games, which I did.
Yes, it's silly, but I was 14, and I've been hooked on VB ever since, and as far as I'm concerned, will program in VB for another 25 years. What's more amazing is that VB6's RAD system for Win32 desktop apps is still without equal in the programming world. No wonder MS has it targeted for destruction. Their ill-advised obsession with .NET absolutely ruined VB. But even without a true VB7, there's very little VB6 can't do for its domain. Especially if you were to say, have a major project dedicated to bringing modern shell features into VB6
In short, I'm not going anywhere. I'll keep this language going into old age
-
Apr 24th, 2021, 07:16 AM
#20
Lively Member
Re: This forum is why VB6 is still usable today
Originally Posted by Schmidt
It probably would (have a place), if there wasn't a huge performance-penalty...
Against all logic, Gosub is about factor 10-15 slower when native compiled
(compared with calling normal sub-routines with a handful of arguments).
....
The above produces (native compiled, all extended options):
- Gosub -> 620msec
- normal Sub -> 40msec
Olaf
yes, I noted that to. But my numbers are quite different (well, on a quite dated computer)
Gosub -> 1258
normal Sub -> 340
So more about a factor of 3 to 4
What do you mean with: 'all extended options'?
Interestingly in the IDE, it's the other way around?? Any insight, why?
-
Apr 24th, 2021, 07:40 AM
#21
Re: This forum is why VB6 is still usable today
Good ol' Faf!
On the subject of gosubs. We should never use gosubs, we all know that - but the language must have gosub or it isn't BASIC.
When programming on a zx80/spectrum 48k/128k (the latter of which I am just rebuilding as we speak) the gosub was one of the most powerful tools in our BASIC armoury. When I progressed to scripting in DCL on VMS (a very powerful scripting language) at that time in DCL's development it only had gosub functionality, no capability for internal callable routines so the BASIC method of calling some code via a gosub carried over very well indeed. You had to be extremely careful about your return statements and the structure of your code.
It certainly taught you to how to debug...
I know this thread has been hijacked by the gosub command but I don't bear any resentment towards it personally. I think BASIC with GOSUB is just not BASIC. It has to be implemented for continuities' sake, as part of the continuing history of BASIC and compatibility of course. I am teaching my boy BASIC, I have to teach him about GOSUB, it is part of what we are.
I mean, we we are talking about it now.
Q. Is there are a case where only GOSUB will do?
-
Apr 24th, 2021, 08:02 AM
#22
Re: This forum is why VB6 is still usable today
Originally Posted by tubus
yes, I noted that to. But my numbers are quite different (well, on a quite dated computer)
Gosub -> 1258
normal Sub -> 340
So more about a factor of 3 to 4
What do you mean with: 'all extended options'?
Sorry, should have used "advanced optimizations" (have translated straight from my german IDE-texts)...
Checking these options, usually accounts for an additional speedup-factor of about 3 (in thight math-related loops).
Originally Posted by tubus
Interestingly in the IDE, it's the other way around?? Any insight, why?
The call-overhead for "entering sub-routines" is higher in IDE- or PCode-mode (compared to native).
Olaf
-
Apr 24th, 2021, 08:32 AM
#23
Re: This forum is why VB6 is still usable today
Originally Posted by yereverluvinuncleber
Q. Is there are a case where only GOSUB will do?
Not really... (since one can always use a real sub-routine instead) -
Only for those who'd want to squeeze out the last bit of performance (in a 5-10% range)
from a "heavy math-routine" which calls a lot of subroutines, GoSub *could* help a bit...
(if it was properly implemented by MS for native-code, which it wasn't)
To show the slight advantage-gain one could get with a properly implemented GoSub,
you can try the example below (where I've used another Goto-Marker for return, to work around the MS-GoSub-issue)
Code:
Option Explicit
Private Sub Form_Click()
Cls
Dim result As Single, i As Long, a As Single, b As Single, T!
T = Timer
For i = 1 To 10 ^ 8
GoTo Calculate1 '<- now we use Goto directly instead of GoSub
Ret_Calculate1: '<- and therefore have to define an additional Marker for the "return-point"
Next
Print "GotoReturn:", CLng((Timer - T) * 1000); "msec", result
result = 0: a = 0: b = 0: DoEvents
T = Timer
For i = 1 To 10 ^ 8
Calculate2 result, i, a, b
Next
Print "Subroutine:", CLng((Timer - T) * 1000); "msec", result
Exit Sub
Calculate1:
a = b / i: b = result + 1
result = a - b
GoTo Ret_Calculate1 'instead of the Return-keyword, we just jump back to our own return-marker
End Sub
Private Sub Calculate2(result As Single, i As Long, a As Single, b As Single)
a = b / i: b = result + 1
result = a - b
End Sub
If you don't want to wait for 10-15sec or so (have increased the loop-count), you should run this code only native compiled...
(to then see a slight advantage of about 6% for the "sub-routine-avoiding" code-part).
Olaf
-
Apr 24th, 2021, 08:41 AM
#24
Lively Member
Re: This forum is why VB6 is still usable today
Originally Posted by Schmidt
Sorry, should have used "advanced optimizations" (have translated straight from my german IDE-texts)...
Checking these options, usually accounts for an additional speedup-factor of about 3 (in thight math-related loops).
Olaf
thanks, that's what I assumed. I have these unchecked too. So why this difference of 10-15 to 3.7 times slower?? (And the numbers are very stable, like +-1)
The call-overhead for "entering sub-routines" is higher in IDE- or PCode-mode (compared to native).
Yes, obviously that is what it means. But why?
Why is a Gosub slower in Native-code than in PCode, against all logic, as you say.
Nonetheless, I have no other option than use Gosub every once in a while, I try hard to avoid it, but sometimes I see no other way.
It's the poor men's 'inheritance' actually.
-
Apr 24th, 2021, 08:49 AM
#25
Lively Member
Re: This forum is why VB6 is still usable today
Originally Posted by Schmidt
Not really... (since one can always use a real sub-routine instead) -
Olaf
...and what do you do if you have a rich Sub with a lot of local variables?
Passing dozens of variables to the Sub? Or making these variables Global? Neither seems a good idea to me??
-
Apr 24th, 2021, 08:52 AM
#26
Re: This forum is why VB6 is still usable today
Originally Posted by tubus
thanks, that's what I assumed. I have these unchecked too.
What I meant was, that you will have to check them all (to see an additional speedup-factor of about 3).
Originally Posted by tubus
So why this difference of 10-15 to 3.7 times slower??
3.7 * SpeedupFactorFromFromCheckingAllAdvancedOptions = 11.1 (roundabout)
Originally Posted by tubus
Why is a Gosub slower in Native-code than in PCode, against all logic, as you say.
I don't know what they did there, to cause such a slow-down of GoSub in native mode
(maybe some CoRoutine-like stuff, implemented via Fibers??)...
Have no time (no tools currently installed on my VM), to check the native binaries for clues...
Maybe the trick or dz32 can give an answer more readily...
Olaf
-
Apr 24th, 2021, 08:58 AM
#27
Re: This forum is why VB6 is still usable today
Originally Posted by tubus
...and what do you do if you have a rich Sub with a lot of local variables?
Passing dozens of variables to the Sub? Or making these variables Global? Neither seems a good idea to me??
Have written a ton of code in the last 30 years with VB6,
but never a Routine which required more than "a handful" of params to pass to sub-routines.
If you have "dozens of arguments" to pass into SubRoutines, then (sorry to say),
this would be just bad design...
(easily avoidable, by e.g. aggregating certain "groups of variables" behind UDT-defs, then passing UDT-Vars ByRef into SubRoutines).
Olaf
-
Apr 24th, 2021, 09:05 AM
#28
Re: This forum is why VB6 is still usable today
GoSubs need to GoAway
-
Apr 24th, 2021, 09:07 AM
#29
Lively Member
Re: This forum is why VB6 is still usable today
Originally Posted by Schmidt
Have written a ton of code in the last 30 years with VB6,
but never a Routine which required more than "a handful" of params to pass to sub-routines.
If you have "dozens of arguments" to pass into SubRoutines, then (sorry to say),
this would be just bad design...
Olaf
... yeah, it probably is, but I have no time and energy to change that really.
But, thinking about it, that may be the cause of this behaviour. May be VB in Native-Code is doing just that. Because the Gosub doesn't work native, it just converts it to a normal Sub and passes *all* of the local variables to it, thereby congesting the stack quite a bit.
-
Apr 24th, 2021, 09:14 AM
#30
Re: This forum is why VB6 is still usable today
Originally Posted by tubus
Because the Gosub doesn't work native, it just converts it to a normal Sub and passes *all* of the local variables to it, thereby congesting the stack quite a bit.
GOSUB is very, very RAD.
-
Apr 24th, 2021, 09:16 AM
#31
Lively Member
Re: This forum is why VB6 is still usable today
Originally Posted by yereverluvinuncleber
GOSUB is very, very RAD.
LOL. Then it's a good thing, isn't it?
-
Apr 24th, 2021, 11:06 AM
#32
Re: This forum is why VB6 is still usable today
Code:
Private Sub Form_Load()
Dim i As Long
i = 0
GoSub mysub
GoSub mysub2
GoSub mysub3
MsgBox i
Exit Sub
mysub:
i = i + 1
Return
mysub2:
i = i + 2
Return
mysub3:
i = i + 3
Return
End Sub
gets converted to the following in pcode..it is the same layout in native code as well, just much more verbose
Code:
4017B8 Form1.Form_Load:
4017B8 F5 00000000 LitI4 0x0
4017BD 71 78FF FStR4 [var_88] ;i variable memory address
4017C0 FD0A 3900 Gosub loc_4017F1
4017C4 FD0A 4700 Gosub loc_4017FF
4017C8 FD0A 5500 Gosub loc_40180D
4017CC 27 04FF LitVar_Missing var_FC
4017CF 27 24FF LitVar_Missing var_DC
4017D2 27 44FF LitVar_Missing var_BC
4017D5 F5 00000000 LitI4 0x0
4017DA 04 78FF FLdRfVar var_88
4017DD 4D 64FF0340 CVarRef var_9C 0x4003 (I4 | ByRef)
4017E2 0A 00001400 ImpAdCallFPR4 rtcMsgBox
4017E7 36 0600 [6 bytes] FFreeVar var_BC var_DC var_FC
4017F0 13 ExitProcHresult
4017F1 6C 78FF ILdRf [var_88]
4017F4 F5 01000000 LitI4 0x1
4017F9 AA AddI4
4017FA 71 78FF FStR4 [var_88]
4017FD FCC9 Return
4017FF 6C 78FF ILdRf [var_88]
401802 F5 02000000 LitI4 0x2
401807 AA AddI4
401808 71 78FF FStR4 [var_88]
40180B FCC9 Return
40180D 6C 78FF ILdRf [var_88]
401810 F5 03000000 LitI4 0x3
401815 AA AddI4
401816 71 78FF FStR4 [var_88]
401819 FCC9 Return
40181B 13 ExitProcHresult
Looks like gosubs run inline with the same parent function context using the same set of variables.
Would have to look into how the GoSub command itself was implemented for where the overhead comes in.
it seems like it should have been faster than a function call seems crazy that its slower.
in nativecode the setup for the gosub call is
Code:
.text:0040199B lea eax, [ebp+var_8C]
.text:004019A1 push eax
.text:004019A2 call ds:__vbaGosub
so in both cases it does literally make a function call into the runtime to transfer execution over
to the inline gosub handler.
Last edited by dz32; Apr 24th, 2021 at 11:21 AM.
-
Apr 24th, 2021, 11:40 AM
#33
Re: This forum is why VB6 is still usable today
Originally Posted by fafalone
GoSubs need to GoAway
This thread is proof that VB developers don't dire, they just GoSub with out Return...
-tg
-
Apr 24th, 2021, 12:59 PM
#34
Re: This forum is why VB6 is still usable today
Originally Posted by dz32
so in both cases it does literally make a function call into the runtime to transfer execution over
to the inline gosub handler.
It looks like __vbaGosub would need to implement a local calling stack (parallel to system stack) which is scoped on current procedure only so the book-keeping has quite a bit of overhead in native.
In p-code both are using the same emulated calling stack so the overhead is the same.
cheers,
</wqw>
-
Apr 24th, 2021, 01:35 PM
#35
Re: This forum is why VB6 is still usable today
Originally Posted by wqweto
... looks like __vbaGosub would need to implement a local calling stack (parallel to system stack) which is scoped on current procedure only so the book-keeping has quite a bit of overhead in native.
Regarding "stack-duplication" - it's what Fibers usually ensure, to allow CoRoutine-like behaviour (without involving new threads) - hence my suspicion in #26, that "stuff like that" is probably involved...
https://docs.microsoft.com/en-us/win...-createfiberex
Olaf
-
Apr 24th, 2021, 01:42 PM
#36
Re: This forum is why VB6 is still usable today
ok there was a little more to it
Code:
.text:00401985 lea edx, [ebp+var_8C]
.text:0040198B push edx
.text:0040198C call ds:__vbaGosub
.text:00401992 test eax, eax
.text:00401994 jnz short loc_40199B
.text:00401996 jmp loc_401A2F ; jmp to actual inline gosub handler
.text:00401A2F loc_401A2F: ;mysub label
.text:00401A2F mov ecx, [ebp+var_18]
.text:00401A32 add ecx, 1
.text:00401A35 jo loc_401AD1
.text:00401A3B mov [ebp+var_18], ecx
.text:00401A3E lea edx, [ebp+var_8C]
.text:00401A44 push edx
.text:00401A45 call ds:__vbaGosubReturn
so the vbaGosub actually does an 8 byte alloc where it stores the return address from the vbagosub call
execution then returns to 0401992 in the parent function,
it is the jmp @0401996 which executes the inline mysub in the context of the parent function.
vbaGosubReturn then uses the alloc that was created in vbaGosub to then modify its own stack return address
then frees the 8 byte alloc
when the ret inside vbaGosubReturn happens, it then returns the next address after the calling vbaGosub call.
this means that the code immediately after the vbagosub actually runs twice!
Code:
.text:0040198C call ds:__vbaGosub
.text:00401992 test eax, eax
.text:00401994 jnz short loc_40199B
.text:00401996 jmp loc_401A2F ; jmp to actual inline gosub handler
vbaGosub sets eax to 0 so when it returns the jnz short loc_40199B will not trigger.
vbaGosubReturn sets eax to 1, so when execution again gets back to 0401992, this time the jnz will trigger
which skips the jmp handler.
its a bit goofy but it is what it is.
so the reason gosub is slow is because there is an alloc/free behind the scenes in every gosub call
and also two calls into the runtime for the vbaGosub/vbaGosubReturn pair.
there are actually 2 values saved to teh alloc (why its 8 bytes) the first value a back link to any previous alloc so they can be nested, the second is the return address for this alloc. see vb code example at bottom.
Code:
ENGINE:6610D2E8 ___vbaGosub@4 proc near
ENGINE:6610D2E8
ENGINE:6610D2E8 arg_0 = dword ptr 8
ENGINE:6610D2E8
ENGINE:6610D2E8 push ebp
ENGINE:6610D2E9 mov ebp, esp
ENGINE:6610D2EB push ebx
ENGINE:6610D2EC push esi
ENGINE:6610D2ED push edi
ENGINE:6610D2EE push 8
ENGINE:6610D2F0 call _ProfMemAlloc@4 ; 8 byte alloc to store the current return addr and a var
ENGINE:6610D2F5 or eax, eax
ENGINE:6610D2F7 jz short OutOfMemory
ENGINE:6610D2F9 mov ebx, [ebp+arg_0]
ENGINE:6610D2FC mov ecx, [ebx]
ENGINE:6610D2FE mov [eax], ecx
ENGINE:6610D300 mov ecx, [ebp+4]
ENGINE:6610D303 mov [eax+4], ecx
ENGINE:6610D306 mov [ebx], eax
ENGINE:6610D308 xor eax, eax <-- 0 eax make sure we dont trigger the jnz and hit the jmp
ENGINE:6610D30A pop edi
ENGINE:6610D30B pop esi
ENGINE:6610D30C pop ebx
ENGINE:6610D30D leave
ENGINE:6610D30E retn 4
ENGINE:6610D30E ___vbaGosub@4 endp
ENGINE:6610D311 ___vbaGosubReturn@4 proc near
ENGINE:6610D311
ENGINE:6610D311 arg_0 = dword ptr 8
ENGINE:6610D311
ENGINE:6610D311 push ebp
ENGINE:6610D312 mov ebp, esp
ENGINE:6610D314 push ebx
ENGINE:6610D315 push esi
ENGINE:6610D316 push edi
ENGINE:6610D317 mov ebx, [ebp+arg_0]
ENGINE:6610D31A mov esi, [ebx]
ENGINE:6610D31C or esi, esi
ENGINE:6610D31E jz short ReturnWOGoSub
ENGINE:6610D320 mov ecx, [esi] ; esi = alloced mem from gosub
ENGINE:6610D322 mov [ebx], ecx
ENGINE:6610D324 mov ecx, [esi+4]
ENGINE:6610D327 mov [ebp+4], ecx ; overwrite return address with one saved from alloc
ENGINE:6610D32A push esi
ENGINE:6610D32B call _ProfMemFree@4 ; free alloc
ENGINE:6610D330 mov eax, 1 <--- triggers the jnz this time
ENGINE:6610D335 pop edi
ENGINE:6610D336 pop esi
ENGINE:6610D337 pop ebx
ENGINE:6610D338 leave
ENGINE:6610D339 retn 4 ; now we return to the address right after the original vbagosub call
ENGINE:6610D339 ___vbaGosubReturn@4 endp
So usage looks like this: (dont run in IDE compiled only)
Code:
Private Type goSubAlloc
backLinkToPrevAlloc As Long
calledFromRetAddr As Long
End Type
Private Declare Function vbagosub Lib "msvbvm60" Alias "__vbaGosub" (ByRef pAlloc As Long) As Long
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (pDest As Any, pSrc As Any, ByVal ByteLen As Long)
Private Sub Form_Load()
Dim p As Long
Dim gsa As goSubAlloc
Dim r As Long
r = vbagosub(p)
CopyMemory gsa, ByVal p, 8
MsgBox " p = " & Hex(p) & vbcrlf & _
"backLinkToPrevAlloc: " & Hex(gsa.backLinkToPrevAlloc) & vbcrlf & _
"calledFromRetAddr: " & Hex(gsa.calledFromRetAddr)
'do it again to see back link filled out..
end sub
Last edited by dz32; Apr 25th, 2021 at 05:57 PM.
-
Apr 24th, 2021, 03:31 PM
#37
Re: This forum is why VB6 is still usable today
Originally Posted by dz32
so the reason gosub is slow is because there is an alloc/free behind the scenes in every gosub call
Allocation being involved explains very much the slowdown.
Meanwhile the whole if (__vbaGosub() != 0) { /* return goes here */ } shenanigans look like someone with experience in setjmp() and fork() in C/C++ designed it.
cheers,
</wqw>
-
Apr 24th, 2021, 05:31 PM
#38
Re: This forum is why VB6 is still usable today
Originally Posted by dz32
...so the reason gosub is slow is because there is an alloc/free behind the scenes in every gosub call
and also two calls into the runtime for the vbaGosub/vbaGosubReturn pair.
Interesting - thanks for digging into that...
Olaf
-
Apr 24th, 2021, 06:22 PM
#39
Re: This forum is why VB6 is still usable today
Wow, the Pentium FDIV bug. That takes me back.
My usual boring signature: Nothing
-
Apr 27th, 2021, 07:36 AM
#40
Re: This forum is why VB6 is still usable today
Last edited by VB6 Programming; Apr 27th, 2021 at 07:43 AM.
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|