Quantcast
Viewing all 1466 articles
Browse latest View live

Calculating probability in VB6

Here's some sample code for using in VB6 that will let you calculate probabilities according to Combinations and Permutations formulas. Combinations tells you the number of ways you can pick items from a set when the order doesn't matter, and Permutations tells you the how many ways you can pick items from a set when order does matter.
Code:

Private Function Factorial(ByVal Value As Long) As Double
    Dim n As Long
    Factorial = 1
    For n = 1 To Value
        Factorial = Factorial * n
    Next n
End Function


Private Function Permutations(ByVal ItemsToPick As Long, ByVal ItemsToPickFrom As Long, ByVal RepeatsAllowed As Boolean) As Double
    If RepeatsAllowed Then
        Permutations = ItemsToPickFrom ^ ItemsToPick
    Else
        Permutations = Factorial(ItemsToPickFrom) / Factorial(ItemsToPickFrom - ItemsToPick)
    End If
End Function


Private Function Combinations(ByVal ItemsToPick As Long, ByVal ItemsToPickFrom As Long, ByVal RepeatsAllowed As Boolean) As Double
    If RepeatsAllowed Then
        Combinations = Factorial(ItemsToPickFrom + ItemsToPick - 1) / (Factorial(ItemsToPickFrom - 1) * Factorial(ItemsToPick))
    Else
        Combinations = Factorial(ItemsToPickFrom) / (Factorial(ItemsToPickFrom - ItemsToPick) * Factorial(ItemsToPick))
    End If
End Function

I got the equations for combinations and permutations from https://www.mathsisfun.com/combinato...mutations.html and simply wrote them as VB6 code to get the functions I posted above.

VB6 WebSocket-PushServer-Demo

This Demo shows, how one can "connect a Browser-GUI" to an existing Desktop-App
("Desktop-App-remoting" - e.g. from any given mobile-device via WLAN-IPs in the URL of their mobile-Browsers)

It depends on the cWebServer-implementation of either the RC5 or RC6 package.
(the Project references RC6 - but is switchable to vbRichClient5-reference and should then work the same way).

It is able to run directly in the IDE, starting-up a webserver-instance,
which then listens on the loopback-interface "127.0.0.1" and Port 8080 by default.

A new Browser-instance (-Tab) of your currently installed default-Browser can be shelled directly from this "Server-Form".
(with the correct URL which matches your current IP and Port-Settings).

The Server-App stands for your own "Desktop-App" (and what it could support with regards to "Browser-remoting").
It has currently implemented a little WebAPI-interface which allows:
- two simple JSON-based Ajax-RPC-calls (to show "Browser-initiated Param-transport and -requests)
- but it also allows a Browser-initiated "Subscribing to two ServerPush-Channels" (Server-initiated Data-Pushing to the Browser-Clients)
1) a simple "current ServerTime push-channel"
2) a simple "Chat-channel", which allows:
2.1) a Message-Reflection (at the serverside) for client-initiated Chat-Message to all connected Clients
2.2) a Server-initiated Chat-Message (via Button on the Server-Form) which is transported to all connected Clients as well

Here is the Demo-Code:
WebSocketPushServer.zip

Have fun,

Olaf
Attached Files

Runtime Tracing (Getting Call Stack)

Found this old zip and article on my machine originally from Visual Studio Magazine. While Not part of the Planet Source Code on github may be of help to someone.

Since forum will Not accept html files, article is in Screenshots.
Attached Images
Image may be NSFW.
Clik here to view.
 Image may be NSFW.
Clik here to view.
 Image may be NSFW.
Clik here to view.
 
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    vs0205bb.zip (65.8 KB)

[VB6] secp256k1 library - generate Bitcoin keys.

This repository contains secp256k1 library adapted for VB6. It also contains the small hashing library which provides RIPEMD-160/SHA256 hashing algorithm adapted for VB6. As a simple example there is a VB6 code which allows to generate keys/address for the Bitcoin (BTC) network. You can then import such keys to a wallet.

Github

COM Interop example. How to use .Net classes in VB6.

Image may be NSFW.
Clik here to view.


More than a few times now, I've seen people asking how to use .Net components in their VB6 applications. As it seems there is some small demand for it, I decided to show an example of how it is done. It is very simple and as such doesn't require that much explanation. The code itself should be easily understandable by anyone with a modicum of VB6/VB.Net experience.

Important Note

In order for the VB6 project in the attachment to work correctly, you MUST open the VB.Net project and compile it. The compiler will automatically register it with COM so it will be usable from VB6. The VB.Net project was created using Visual Studio 2019 so I recommend using that version of Visual Studio to compile it.

You can also look at this post I made a few years ago for another example of using COM Interop to access .Net classes from VB6. That example is even simpler than this one.

Any questions are welcomed.
Attached Files

Code snippet (for Add-In) to fix .vbw (workspace) issue

It didn't seem worthwhile creating an Add-In just for this (it seems more appropriate that it be incorporated into other addins), hence posting as a snippet...

Don't know about anybody else, but the IDE's insistence, upon opening a project, of randomly restoring windows, is one VB6 development annoyance that I've lived with for a long time.

Anyway, whilst in the process of developing a related Add-in, I applied my new-found familiarity with the IDE object model, to come up with this:

Somewhere in your Add-In, you'll need a reference to VBIDE.VBProjectsEvents

e.g.
Code:

Private WithEvents mProjectEvents As VBIDE.VBProjectsEvents

...

Private Sub mProjectEvents_ItemRemoved(ByVal VBProject As VBIDE.VBProject)
  SaveVBWFile VBProject
End Sub

...and the following code, which you can put in a module (or wherever)


Code:

Option Explicit
Private Declare Function DeleteFileW Lib "kernel32" (ByVal lpFileName As Long) As Long

Public Sub SaveVBWFile(ByRef VBProj As VBProject)
Dim FileNo As Integer
Dim FilePath As String
Dim s() As String
Dim ComponentName As String
Dim W As VBIDE.Window
 
  FilePath = Replace(VBProj.FileName, ".vbp", ".vbw")
  DeleteFileW (StrPtr(FilePath))
 
  FileNo = FreeFile
  Open FilePath For Output As #FileNo
     
      For Each W In gVBInstance.Windows
        'Window captions take the form 'Project Name - Component Name (type suffix)', where Project name
        'can be absent if the Component belongs to the Active Project

        If W.Type = vbext_wt_CodeWindow Then
            'strip the suffix - we're not intersted in that
            s = Split(W.Caption, " (")
          'If Project name is missing, add it in
            If InStr(s(0), " - ") = 0 Then s(0) = gVBInstance.ActiveVBProject.Name & " - " & s(0)
          'Now attempt to replace the Project Name...
            ComponentName = Replace(s(0), VBProj.Name & " - ", vbNullString)
          '...if that worked, we are interested in this Window
            If InStr(ComponentName, " - ") = 0 Then
              Print #FileNo, ComponentName & " = " & W.Left & "," & W.Top & "," & W.Width & "," & W.Height & ",0,0,0,0,C"
            End If
        End If
      Next W
 
  Close #FileNo
 
End Sub

It's not perfect, as it won't allow you to save vbw data for Designer Windows. Unfortunately, by the time mProjectEvents_ItemRemoved fires, all such windows have already been destroyed. Still, I can live with that versus the chaos that the IDE sometimes inflicts on me.

ID Card Creator

I was looking thru some old code samples and decided to make this app. Hopefully I have everything working as it should. See what you think.
Attached Images
Image may be NSFW.
Clik here to view.
 
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    IDMaker.zip (96.4 KB)

[VB6] Encode binary data to bitmap for use in a PictureBox

If you've ever tried to include more than a very small amount of binary data on a Form or UserControl without loading the data from an external file, you certainly noticed it's extremely difficult to accomplish. There's limits to how much data can be stored in string constants, trying to store in controls like a ListBox as the ListItems runs into huge problems when it's more than a tiny file... and just all sorts complications with various ways.

But thanks to an idea by LaVolpe and implementing code from The_trick, there's a simple and effective way to get binary data onto your form. It's possible to encode binary data as a bitmap, and set that bitmap as the Picture in a standard PictureBox.

I used this method in my ucShellBrowse UserControl to store icons for menus and buttons, I included this tool attached to the 2nd post and there were so many downloads of the tool that I wrote around The_trick's code that I wanted to post this as an independent code sample for all the people who might not come across it in that project.

Image may be NSFW.
Clik here to view.
Name:  bmpenc.jpg
Views: 5
Size:  42.5 KB

There's two projects in this sample. An Encoder demo, and a Decoder demo. The demo includes a preprocessed sound-- the Encode directory contains TestSound.wav, and the Decode project includes the processed bitmap, Enc-TestSound.wav.bmp, set as a Picture and ready to be decoded. You can use the Encoder for other files, and the Decoder also has a function to write it back to file. There's a sample icon that includes the original and processed, but it's not set to a PictureBox yet. Note that the .bmp files are intermediates; once you've set it as a picture on your form, they're no longer needed- you don't need to include them with the project, that would defeat the whole point :)

To test it on your own file, enter the directory and name in the Encode demo, and click process. That generates the bitmap. Then in the Decode demo, in the IDE set it as the Picture for the PictureBox on the bottom. Then click Decode to file- a Save dialog will come up, and you save it as its original type. That file will come out identical to the input file you started with.



This project has no external dependencies. It should run on any version of Windows.
Thanks again to LaVolpe and The_trick. The_trick wrote the central encode/decode function, all I did was build a demo around it.
Attached Images
Image may be NSFW.
Clik here to view.
 
Attached Files

My 3DText usercontrol

My version of a 3d text usercontrol. Makes great looking labels. Its pretty simple, so hopefully you can use it.
Attached Images
Image may be NSFW.
Clik here to view.
 
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    ucMy3D.zip (3.9 KB)

Numbers, Numbers, Numbers

This package contains a large set of library routines I have built over the years to do many things related to numbers. These routines run in VB6 as well as 32 or 64-bit VBA. As you know, there are often multiple ways of solving a problem. I have been building these utilities for 20+ years and I often work on speed, accuracy and functionality for all of them. If you have any procedures that you think are “better” than those I have in this package please let me know so I can upgrade the library.

A lot of the routines use normal VB code. For some I have used RtlMoveMemory (many of you use an alias of CopyMemory for this Windows API function) to facilitate things like shifting bits, copying to other data types (e.g., getting the top byte of a Long variable into a Byte) etc.
In general I have found that I do not include an entire module but rather use specific ones you need in my code.

The package consists of 9 modules and is there are no dependencies. Most of the subs and functions are self-explanatory but each is briefly discussed below. BTW, if you use any of this in Excel as User Defined Functions, you can greatly improve the time lag in the workbook by putting the “Application.Volatile False” at the top of whatever function(s) are using in the spreadsheet.

At the end of this document are instructions for running the sample code.

mBaseConversions

This module allows for conversion between regular numbers, hexadecimal and binary.

This module makes use of a variable I call UVar which represents an unsigned Currency which allows us to use all 64 bits of the number. If you are using 64-bit VBA then you can also think of UVar as an unsigned LongLong (also 64 bits). A UVar can be a Byte, Integer, Long, Currency, Single, Double, Decimal (part of a Variant) and a LongLong (64-bit only).

What you submit to this function (and the others in this module) are treated as unsigned values. As you know, VB uses the top bit of scalar variables to designate the sign. We ignore that and treat the topmost bit as just another bit. For example, the hex value of -1 as a Long is &HFFFF (i.e., all bits are set). BTW, you can’t avoid the top bit being used for the sign. It would be tempting to think you can take and integer value of -1 and use the function to convert it to a Long that the full 16 bits would go to the Long. Unfortunately, VB doesn’t do that. Instead, VB converts the Integer -1 to a Long -1 (all 32 bits in the Long are set whereas only 16 bits were set in the Integer. For normal use this is okay but when we want to use all of the bits in hex or binary, this is a problem. Other than a Byte, VB doesn’t have any unsigned variables so that’s what we deal with here.

One interesting thing occurs with the Currency variable. Even though it is an integer type variable, it has a decimal component. VB does this by taking the value given it an multiplying by 10,000 and then it uses the lower bits to do the fractional part. Internally it is just a 64-bit value and the multiplying and dividing by 10,000 is done when a value is assigned or the conversion function CCur is used. We treat a Currency value as an unsigned 64-bit value. If you have a regular Currency variable and you want to feed it to UVar2Hex or UVar2Bin then you should first divide it by 10,000. Likewise, if you use Hex2UVar or Bin2UVar and you want to use the return Currency value for other calculations you should multiply it by 10,000.
If you use this in 64-bit Office you have access to a signed 64-bit variable called a LongLong that does not have the 10,000 factor that the Currency data type has. The only thing to watch out for is that it is a signed variable (i.e., the topmost of the 64 bits is the sign bit).

UVar can also be a Single, Double or a Decimal value but note that when you use UVar2Hex or UVar2Bin with a negative number it gets converted to a signed value. For example, if you have a Double variable with a value of -1, when it gets converted it will become an integer (Currency or LongLong) with a value of -1. If that’s what you wanted that’s fine but just know that with anything other than a Byte data type, you have to be aware that VB messes around with the topmost bit. It would be nice if VB had unsigned variables but it doesn’t so this is why I created this set or procedures.

Function UVar2Hex – Return a hex string from the UVar. The return will have no leading zeroes (e.g., Feeding it a Long value of 10000000& returns “98 9680” and not “0098 9680”). You can determine whether to group the return characters, and if so, how much (the example in the previous was based on the default grouping of 4 characters).

The function specifies the input variable is a Variant but you can use whatever data type you want without first converting it to a variant (I believe VB does that internally).

Function Hex2UVar – Convert a hex string (up to 16 characters (64-bit)) into an unsigned value. You can specify a data type or take the default which is to determine the data type from the size of the value. For example, if you pass “F” as the hex string, you could specify for it to be returned as a byte, integer, long, etc. but if you go with the default it will be returned as a byte inside the variant.

Function UVar2Bin – Converts an unsigned variable into its binary equivalent (as a string). For a Byte, Integer, Long, Currency, LongLong, Single, Double or Decimal returns the string representation of the binary number (base 2). Since the routine uses an unsigned value, if you use a Currency then it should first be divided by 10,000 (or as part of the call) to use all of the bits.

There is an optional parameter named RndType (optional) determines the size of the return number (higher bits are discarded from return). For example, if you pass an integer with a value of 111, this function will return “00000000 01101111” but if you set RndType to 1 to indicate a Byte, the function will return” 01101111”. You can specify what character (or none at all) to sue as the leading character. For example, if you specify no leading character, the return from the previous example will be “1101111”. Finally, you can set the grouping. The previous examples use a grouping of 8 characters. If you specify 0 there is no grouping and the string is returned without any spacing characters.

Function Bin2UVar - Returns the variable related to the binary string of up to 64 characters (1s and 0s). Must specify the variant variable type in "VarType" (vbByte, vbInteger, vbLong, vbCurrency or vbLongLong) and the return is adjusted for the type of variable. If you do not specify this value then the function determines it from the length of the input binary string (1-8 byte, 9-16 integer, 17-32 long, 33-64 currency or longlong).

Function Hex2Bin - Converts a hex string into its binary counterpart. As discussed above, you can also specify the leading character (defaults to 0) or you can not have leading zeroes by specifying “”. You can also set the grouping of binary characters in the return (default 8 characters which is 1 byte).

Function Bin2Hex - Converts a binary string of up to 64 characters (all 0's and 1's) into a hex string.

Module mBaseConversions1

The previous module has very flexible routines for converting between base 10, hexadecimal and binary numbers. If you want type-specific solutions that have fewer frills, the following conversions could be used.

Byte2Hex – Returns the hexadecimal representation of a Byte with optional leading 0’s.

Int2Hex – Converts an Integer into a Hex.

Long2Curr – Converts an unsigned Long to a Currency.

Long2UCurr – Returns an unsigned Currency with the Long in the low order bytes.

Long2Bin1 – Converts a Long into a binary string. Same functionality as Bin2Hex in module mBaseConversions but uses different logic & has a different name to avoid duplicate names in the same project.

Long2Hex – Converts a Long variable into a Hex string.

Curr2Hex – Converts a Currency into a hex string.

Curr2Bin – Converts a Currency into a binary string.

UCurr2Hex - An unsigned Currency (if it is a “normal” Currency, it should be divided by 10,000). This function converts this unsigned Currency into a Hex string.

Bin2Byte – Converts a binary string into a Byte.

Bin2Int – Converts a binary string into an unsigned integer (uses last 16 bits).

Bin2Long – Converts a binary string into a Long.

Bin2Curr – Converts a binary string into a Currency. Unlike Bin2UVar, this one returns the Currency without using the last 4 bits (i.e. not divided by 10,000).

Bin2UCurr – Converts a binary string into the unsigned Currency.

Bin2Hex1 – Converts a binary string into its hex equivalent. Same functionality as Bin2Hex in module mBaseConversions but uses different logic & has a different name to avoid duplicate names in the same project.

Hex2Curr – Converts a hex string into a Currency.

Double2Hex – Converts a Double into its hex equivalent.


If you are using 64-bit VBA you also have the following procedures:

Long2LL – Converts an unsigned Long into an unsigned LongLong.

LLToHex – Converts an unsigned LongLong into its Hex equivalent.

Bin2LL – Converts a binary string into an unsigned LongLong (string, max 62 chars)

Hex2LL – Converts a hex String (up to 15 characters) into an unsigned LongLong.

LL2Hex – Converts an unsigned LongLong into hex.

LL2Bin – Converts an unsigned LongLong into a binary string.


Module mDataTypeConversions

This module works with sub-parts of variables. For example, one function takes all 4 bytes of a Long and puts them into 4 Byte variables.

Bytes2Int – Puts 2 Bytes into the 2 bytes of an Integer.

Bytes2Long – Puts 4 Bytes into one Long.

Bytes2UCurr – Combines 8 Bytes into a Currency (not multiplied by 10,000).

Int2Bytes – Puts the 2 bytes of an Integer into 2 Bytes.

Ints2Long – Puts 2 Integers into a Long.

Ints2UCurr – Combines 4 Integers into a Currency (not multiplied by 10,000).

Int2LoByte - Returns the low byte (least significant byte) of "Integer1"

Int2HiByte - Returns the high byte (most significant byte) of "Integer1"

Long2Byte - Puts the specified byte (1=least significant byte, 4=most significant byte from a Long into a Byte.

Long2Bytes – Puts the 4 bytes of a Long into 4 Bytes.

Long2Ints – Puts the two integers making up the most and least significant words of a Long into 2 Integers.

LongToUCurr - Takes a long (unsigned but contained in a signed long) like from an API call & returns it in a U64 (NOT multiplied by 10,000). Note – the top 4 bytes of the U64 value will always be 0 by definition.

Longs2UCurr – Combines 2 Words into a Currency (not multiplied by 10,000).

Long2LoWord - Returns the low integer (least significant word) of a Long into an Integer.

Long2HiWord - Returns the high integer (most significant word) of a Long into an Integer.

Long2CurrLo – Puts a Long into the low 4 bytes of a Currency (hi bits are 0).

Curr2UCurr - Takes a Currency that VB has already multiplied by 10000. Existing fractional part is discarded.

UCurr2Bytes – Puts the 8 bytes of a Currency (not divided by 10,000) into 8 Bytes.

UCurr2Ints – Puts the 8 bytes of a Currency (not divided by 10,000) into 4 Integers.

UCurr2Longs – Puts the 8 bytes of a Currency (not divided by 10,000) into 2 Longs.

UCurr2Byte – Puts the selected byte of a Currency into a Byte.

UCurr2Int – Puts the selected word of a Currency into an Integer.

UCurr2LoLong - Returns the low long (least significant long) of a Currency.

UCurr2HiLong - Returns the high long (most significant long) of a Currency.

UCurrToCurr - Takes a 64-bit value that VB has NOT multiplied by 10,000 and does that to the number (for display & non-bit calculations).

If you are using 64-bit VBA you also have the following procedures:

LL2Bytes – Puts the 8 bytes of a LongLong into 8 Bytes.

LL2Ints – Puts the 8 bytes of a LongLong into 4 Integers.

LL2Longs – Puts the 8 bytes of a LongLong into 2 Longs.

Bytes2LL – Puts 8 Bytes into a LongLong.

Ints2LL – Combines 4 Integers into a LongLong.

Longs2LL –Combines 2 Longs into a LongLong.

Long2LLLo – Puts the 4 bytes of a Long into the low 4 bits of a LongLong (hi 4 bytes are 0’d).

LL2Byte - Puts the specified byte (1=least significant byte, 8=most significant byte out of a LongLong into a Byte.

LL2Int - Puts the specified integer (1=least significant integer, 4=most significant integer out of a LongLong into an Integer.

LL2LoLong - Puts the low long (least significant long) of a LongLong into a Long.

LL2HiLong – Puts the most significant 4 bytes of a LongLong into a Long.


Numbers.zip

{Continued in next post}
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    Numbers.zip (70.9 KB)

[Add-In] IDE Code-Pane Tabs for MDI/SDI (No sub-classing/hooking)

Background
I'm not much of Add-In user, but my liking for a tabbed interface of open code windows has meant that CodeHelp has been a permanent fixture of my IDE for a few years now. Just recently, I thought I'd develop an Add-In of my own, and wondered if I could improve on the CodeHelp offering. Whether I have or not, will be a matter of personal opinion, as I only focussed on the things that I wanted to change, without regard for any features that I, personally, do not use.

Things I like about CodeHelp's tabstrip:
1) It's always available, whether in Design, Run or Break mode
2) You can re-order the tabs to your liking (although it's a bit clunky-feeling)

Things I don't like:
1) It has lots of sub-classing and hooking, which gives me stability concerns
2) You can't close a tab without activating it first
3) You can't re-order the tabs without first activating the tab you are moving
4) Sometimes the active tab gets out of sync with the active code pane

About my Tab-Strip
I tried, of course, to retain everything from my 'positive' list, whilst eliminating those that (to me) are negatives. I suspect that other users may have quite different lists, such as keyboard shortcut access, and so on. If so, I'd like to hear from you in the replies. Maybe I can then incorporate those features. Or maybe you can modify the code as you see fit...

Anyway, this add-in, as the title says, can be used in both MDI and SDI modes, and contains no sub-classing or hooking. Instead, it uses a simple polling mechanism which does two tests, every 125ms, essentially asking:

1) Has the active window changed?
2) Has the number of IDE windows changed?

If either of those is true, things get taken a step further and all of the windows are enumerated, and the tab-strip is updated if there are any recently-closed or newly-opened code/designers windows. All-in-all, this should be pretty IDE-safe, and is actually less process-intensive than testing Window messages as they come by. It is only a tab-strip after all, and just doesn't require the level of 'state-awareness' that hooking/sub-classing might afford.

So, here it is:

Image may be NSFW.
Clik here to view.
Name:  Untitled.jpg
Views: 116
Size:  28.6 KB



What Else?

I have commented out all the logging code, but if you need/want to turn this on, there is a hidden listbox in frmTabStripOptions (just resize the form to see it)

Oh, yes, the UserControl is perfectly re-usable outside of this Add-In, if you like it and want such a thing.


Known Issues

MDI Only
None, yet, but I'm sure somebody will find one!

SDI Only
Window captions for Forms are not in the format 'Project - Component' but, instead, show the caption property for the form. As such, any caption re-naming is not picked up as part of the polling process. This could be addressed, but just doesn't seem worthwhile, at least not to me.

Both
Because the Tab-Strip is hosted by a regular Office toolbar, it is possible to drop another toolbar on top of it. Not sure anything can be done to prevent this behaviour.

When pressing F5, all designer windows are immediately closed (normal behaviour), but the same is not true (at least not consistently) for the Object Browser, which seems to sometimes remain open and sometimes get closed. As such, the tabstrip might occasionally show a tab for a non-existent Object Browser window, depending on when the IDE chooses to destroy it (if at all), and whether or not it was the active window when F5 was pressed.



To Do
  • Add those little scrolling buttons to the ends of the tabstrip. For now you can Ctrl-drag the whole tabstrip to do the same job.
  • Add some options (font size, right-click behaviour, etc.) I feel that there's potential for such 'click-behaviour' options to apply more to SDI layouts, for some reason (e.g. right-click a tab to maxmize). But maybe that's just me finding SDI a bit chaotic!
  • Add a 'Max tab width' option, as suggested in Post #2
  • Options to close multiple tabs in one operation, as suggested in Post #2
Attached Images
Image may be NSFW.
Clik here to view.
 
Attached Files

Certificate Verify

My knowledge of ECDSA Certificate handling was minimal, but in order to produce a TLS 1.3 web server, RFC 8446 requires support for digitial signatures. So after a laborious learning experience, I decided to post what I learned.

The private key is recovered from the "privkey.pem" Base64 encoded file, decoded to ASN.1 format, and finally to a Private EC Key.
Code:

Base64 Encoded File:
-----BEGIN EC PRIVATE KEY-----
MHcCAQEEIMrOBboK+r8CzXUj6EJG67fUX9UGz2K+sMFsGiOlZQProAoGCCqGSM49
AwEHoUQDQgAEU0GMUttccTAXPsGYQyrF0gZt0KuRWpmnq8Zt0IvG6ZwrMoPg9slF
sXYQOQ8hOKkQwLYzKbQgifvKw6aB/xnLtQ==
-----END EC PRIVATE KEY-----

ASN.1 Private Key:
30 77 02 01 01 04 20 CA CE 05 BA 0A FA BF 02 CD
75 23 E8 42 46 EB B7 D4 5F D5 06 CF 62 BE B0 C1
6C 1A 23 A5 65 03 EB A0 0A 06 08 2A 86 48 CE 3D
03 01 07 A1 44 03 42 00 04 53 41 8C 52 DB 5C 71
30 17 3E C1 98 43 2A C5 D2 06 6D D0 AB 91 5A 99
A7 AB C6 6D D0 8B C6 E9 9C 2B 32 83 E0 F6 C9 45
B1 76 10 39 0F 21 38 A9 10 C0 B6 33 29 B4 20 89
FB CA C3 A6 81 FF 19 CB B5

Private Key:
04 53 41 8C 52 DB 5C 71 30 17 3E C1 98 43 2A C5
D2 06 6D D0 AB 91 5A 99 A7 AB C6 6D D0 8B C6 E9
9C 2B 32 83 E0 F6 C9 45 B1 76 10 39 0F 21 38 A9
10 C0 B6 33 29 B4 20 89 FB CA C3 A6 81 FF 19 CB
B5 CA CE 05 BA 0A FA BF 02 CD 75 23 E8 42 46 EB
B7 D4 5F D5 06 CF 62 BE B0 C1 6C 1A 23 A5 65 03
EB

Then the Magic string is added to form the Blob, which is used to sign the extended Session Hash, which is then ASN.1 encoded to form the Certificate Verify record. Note that the Compression byte (&H04) is overwritten and not required.
Code:

Private Key Blob:
45 43 53 32 20 00 00 00 53 41 8C 52 DB 5C 71 30
17 3E C1 98 43 2A C5 D2 06 6D D0 AB 91 5A 99 A7
AB C6 6D D0 8B C6 E9 9C 2B 32 83 E0 F6 C9 45 B1
76 10 39 0F 21 38 A9 10 C0 B6 33 29 B4 20 89 FB
CA C3 A6 81 FF 19 CB B5 CA CE 05 BA 0A FA BF 02
CD 75 23 E8 42 46 EB B7 D4 5F D5 06 CF 62 BE B0
C1 6C 1A 23 A5 65 03 EB                       

Hash:
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20
54 4C 53 20 31 2E 33 2C 20 73 65 72 76 65 72 20
43 65 72 74 69 66 69 63 61 74 65 56 65 72 69 66
79 00 C8 A1 31 6D 80 8B BE C9 60 3B 1B CF 57 2B
99 02 8C B0 0A 64 7A BE C5 93 AA 88 6C C8 60 70
78 54                                         

Signed Hash:
99 B5 49 9B D1 4D 82 52 19 CA E5 EC E8 A2 49 81
59 57 21 19 4B 67 8B 2A 62 19 71 21 E6 94 19 5E
99 A4 E7 12 CA 7A 0E 8D BE D2 F3 E0 C8 7C EE EC
B9 52 D9 F8 F4 07 25 2C 61 BF 77 64 C5 75 32 88

Cert Verify:
0F 00 00 4B 04 03 00 47 30 45 02 20 5E 19 94 E6
21 71 19 62 2A 8B 67 4B 19 21 57 59 81 49 A2 E8
EC E5 CA 19 52 82 4D D1 9B 49 B5 99 02 21 00 88
32 75 C5 64 77 BF 61 2C 25 07 F4 F8 D9 52 B9 EC
EE 7C C8 E0 F3 D2 BE 8D 0E 7A CA 12 E7 A4 99

That record is then encrypted and sent to the client directly after the Certificate itself. At the client end, the Cert Verify is decrypted, then ASN.1 decoded to get the signed hash. The Public Key is normally extracted from the Certificate, but in this case I extracted it from the Private Key. If anyone knows of an efficient way to extract the key from the Certificate, I would be very interested. Anyway, the Public Key Blob and the Signature are fed into the BCryptVerifySignature function and verified. That routine supposedly wants the original Hash itself, but I discovered that it only needs a 32 byte string (no explanation offered).
Code:

Public Key Blob:
45 43 53 31 20 00 00 00 53 41 8C 52 DB 5C 71 30
17 3E C1 98 43 2A C5 D2 06 6D D0 AB 91 5A 99 A7
AB C6 6D D0 8B C6 E9 9C 2B 32 83 E0 F6 C9 45 B1
76 10 39 0F 21 38 A9 10 C0 B6 33 29 B4 20 89 FB
CA C3 A6 81 FF 19 CB B5                       

Certificate Hash:
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20
20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20

Hash Signature:
0C 06 0A AA 8F 7A 44 20 C7 DD FE A6 CF 2D 63 31
02 A1 29 B3 27 8E 36 72 77 04 B3 C8 90 A4 CF 61
9E 90 AC CC DC 6E F5 46 5B 9E C7 EF 1B 2C DE 5E
0A 7E B9 0B 00 55 D6 C2 06 F3 CE 7D F4 3D F0 BD

Certificate Verified!

There are a few extra buttons that directly demonstrate some functions.
1. Verify Test - This routine demonstrates what happens when a Private key does not match the Public key.
2. Convert String - This was added because I used a different method to convert a Unicode ASCII string to a byte string and back again. I am hoping that this new routine handles ASCII values greater than &H7F, and is more efficient than my old routine.
3. Cert Verify - This routine demonstrates the conversion of an ASN.1 encoded key to a Base64 encoded file format.

J.A. Coutts
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    CertMgr.zip (5.9 KB)

Binary Converter-Very simple

Looking for a simple binary converter. It doesnt get any simpler than this one.
Attached Images
Image may be NSFW.
Clik here to view.
 
Attached Files
  • Image may be NSFW.
    Clik here to view.
    File Type: zip
    Binary.zip (3.2 KB)

[VB6] VBCDeclFix - The Add-in allows you to use Cdecl functions in VB6 IDE.

The Add-in allows you to use Cdecl functions in VB6 declared in type libraries.

If you have ever tried to use CDECL-functions declared in a TLB then you know that debugging (in IDE) is impossible. The project just has crashed and doesn't even start although compilation to native code works without any issues. This Add-in fixes this behavior and you can debug your code in IDE.

https://github.com/thetrik/VBCDeclFix

QR decode encode support utf-8 without using third parts software, external DLL,OCX?

hi,i am searched in google to can find any vb6 source code QR generator and decoder without any dll,ocx or like this but i cant find good samples,for example i found this :

its just exe sample without any dll or ocx or ... :
- http://www.luigimicco.altervista.org...-visual-basic/

or i found some sources with rc5 like this (its used external dll):

VB6 QR-Encoding+Decoding and IME-Window-Positioning

or

leandroascierto

but it works with online services like as zxing.org.

so i created new project and used some classes from another projects about qr and completed 50% with support these :
image link
Image may be NSFW.
Clik here to view.

- generate QR
- supported utf-8
- supported shift-jis
- supported save as bmp,gif,jpg(variable quality),png
- supported error correction
- supported display and export good size per pixel.
- supported backcolor and forecolor

but i want complete my project with decode QR too without external dll or ocx or online website services,so any body here have any user control or sample source to can decode without online sevices sites or ocx or dll?

events for late-bound objects (vb6 com events IIDSTR_IConnectionPointContainer)

VB6 SHOW 3DMAX (Cult3D ActiveX Player),CO File format

Cult3D ActiveX Player

Cult3DP1.Visible = True
Cult3DP1.LoadCult3D App.Path & "\sun.co"

download 3d ocx:
http://www.web3d.com.cn/plugin/cult3d.html

how to use Cult3DP1?
Cult3DP1.***
Private Sub Cult3DP1_OnSendMessage(ByVal Message As String)
Me.Caption = "Message=" & Message
End Sub

VB6 2D-ChartPlotting (using the RC6.cChart HelperClass)

Just a little Demo, how to work with the new RC6.cChart-Class (requiring an RC6-version >= 6.0.3).

This Class follows a somewhat different pattern, compared to other Chart-Controls -
because it supports a "virtual concept" which:
- doesn't define the Chart-behaviour (or Type) as much via Properties
- but via OwnerDraw-Events instead

To "catch" these Events (to draw your own "ChartType"):
- you have to define your own Class (per ChartType)
- and in this Class, you will receive the OwnerDraw-Events

Example for such a UserDefined CharType-Class
(taken from the zipped example below, responsible for rendering the chart at the right-hand-side of the following ScreenShot):
Code:

Option Explicit

Public WithEvents Chart As cChart

Private Sub Class_Initialize()
  Set Chart = New_c.Chart
End Sub
 
'**** Class-specific Implementation of the Chart-Events *****
Private Sub Chart_DrawChartBackGroundAndTitle(CC As cCairoContext, ByVal Title As String)
  CC.Paint 1, Cairo.CreateSolidPatternLng(vbWhite)
  CC.SelectFont "Times New Roman", 13, &H222222, True, True
  CC.DrawText 0, 0, CC.Surface.Width, 50, Title, True, vbCenter, 3, True
End Sub
 
Private Sub Chart_OverrideAxisProps(Axis As cChartAxis, ByVal CurrentMin As Double, ByVal CurrentMax As Double, ByVal CurrentTickIntervals As Long)
  If Axis.Name = "X" Then Axis.TickIntervals = 10
End Sub

Private Sub Chart_DrawSingleTickForAxis(Axis As cChartAxis, CC As cCairoContext, ByVal TickValue, ByVal x As Long, ByVal y As Long, ByVal dx As Long, ByVal dy As Long)
  Select Case UCase$(Axis.Name)
    Case "X"
      CC.DrawLine x, y, x, y + dy + 4, True, 1, vbRed, 0.5
      Axis.DrawTickText CC, x, y + 6, Format$(TickValue, "0.00")
    Case "Y"
      CC.DrawLine x - 4, y, x + dx, y, True, 1, vbBlue, 0.5
      Axis.DrawTickText CC, x - 4, y, Format$(TickValue, "0.00")
  End Select
End Sub
 
Private Sub Chart_DrawData(CC As cCairoContext, DataArr() As Variant, ByVal dx As Long, ByVal dy As Long)
  Dim PolyArr As cArrayList
  Set PolyArr = Chart.GetAxisScaledPolyArrXY(DataArr, Chart.AxisCol("X"), Chart.AxisCol("Y"))
 
  CC.SetLineWidth 2
  CC.PolygonPtr PolyArr.DataPtr, PolyArr.Count \ 2, False, splNormal, True, True
  CC.Stroke , Cairo.CreateSolidPatternLng(vbGreen)
End Sub

Here a ScreenShot:
Image may be NSFW.
Clik here to view.


Here is the zipped Demo-Code, which produced the above output:
ChartPlot.zip

Have fun,

Olaf
Attached Files

[Add-In] Large Project Organiser (alternative Project Explorer) - No sub-classing!

Undeterred by the lukewarm reception of my tab-Strip Add-In :D, here I am with another one. Gotta fill-up those lock-down days doing something, eh?

This one is thought as a replacement for the built-in Project Explorer, and may be useful to somebody who is working with a large project. The idea (and not an original one!) is that you can organise your projects into something more meaningful than simply a list of Component Types: As illustrated below, create appropriate Groups and drag/drop into those

Overview

Image may be NSFW.
Clik here to view.



Cloning

And one is not limited to doing this on a one-to-one basis, either. Here I am cloning an item into more than one Group (via the CTRL key), just to show that that's possible, too:


Image may be NSFW.
Clik here to view.



Ordering

And, finally, one can order the Groups, however they see fit....

Image may be NSFW.
Clik here to view.


Download

...and here's the code:

ProjEx Addin.zip

Updated with the problem identified in post #2 fixed.
Attached Files

vb6 Secure Websocket

Secure webSocket in Pure VB6 no external Libraries or ActiveX.
Now wss://localhost:8088 is possible.
Now Lengthy(char length more than 65536) messages possible.

Thanks goes to :
Vladimir Vissoultchev(wqweto)
Olaf Schmidt
and many others.
https://github.com/wqweto/VbAsyncSocket

https://www.vbforums.com/showthread....ushServer-Demo

https://github.com/bloatless/php-websocket

https://www.cnblogs.com/xiii/p/5165303.html



In order to create a self-signed ssl certificate you need open-ssl. In my case I have done it in my cloud server and downloaded.
Follow the instructions given here :

https://www.freecodecamp.org/news/ho...-7af615770eec/

after install the certificate. open rootCa.crt -> Install Certificate - > Next -> Place all certificates in the following store -> Browse
-> Trusted Root Certification Authorities - > OK -> Next - > Finish - > Install/Approve

Download the attachment
vb-websocket.zip

Notes:

I have combined and ported codes from here and there, and given the references, detailed code explanations can be found there.
Attached Files
Viewing all 1466 articles
Browse latest View live


<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>