VB6 IP4 - 根据位数计算网络掩码(长)

时间:2010-02-20 01:55:27

标签: vb6 performance ip-address bit-manipulation cidr

给定0到32的输入,表示IP4网络掩码中的一位数(对应于/ 19中的CIDR块大小),是什么

  1. 将其转换为四字节长网掩码的优雅方式
  2. 将其转换为四字节长网掩码的快捷方式
  3. 原型:

    Function NetMaskFromBitCount(BitCount As Long) As Long
       'Logic here '
    End Function
    

    请注意,VB6不做无符号这一事实很复杂,因此常规数学技巧通常不起作用。如果(Number And &H80000000)非零,则Number \ 2将与SHR操作不同。

    我想出了一些方法,但我不认为它们很优雅,而且它们可能不那么快。

    我的一个想法是战略性地使用CopyMemory API,这非常快。我已经解决了过去的一些有符号/无符号Long问题,只需将Long分成一个字节(0到3)并根据需要处理每个部分。

    由于我还在使用inet_ntoa()和inet_addr()Windows API函数,并且它们以反向字节顺序返回IP序列号,因此以相反顺序返回字节的解决方案很棒(我已经有了一个函数如果需要,可以翻转字节顺序,但是避免它也很好。

    示例:

    Input = 2
    Output = -1073741824 (&HC0000000)
    Alternate Output = 12 (&HC0, reverse byte order)
    
    Input = 19
    Output = -8192  (&HFFFFE000)
    Alternate Output = 14745599 (&H00E0FFFF, reverse byte order)
    

    工作解决方案很好,但是我正在寻找ELEGANT或FAST。

3 个答案:

答案 0 :(得分:1)

Function NetMaskFromBitCount(ByVal lBitCount As Long) As Long
    If lBitCount > 0 Then
        NetMaskFromBitCount = -1 * 2 ^ (32 - lBitCount)
    End If
End Function

对不起匈牙利人:-))不得不制作这个参数ByVal

测试就在这里:

Debug.Assert NetMaskFromBitCount(19) = &HFFFFE000
Debug.Assert NetMaskFromBitCount(2) = &HC0000000
Debug.Assert NetMaskFromBitCount(32) = &HFFFFFFFF
Debug.Assert NetMaskFromBitCount(0) = 0

答案 1 :(得分:1)

您只有32个可能的输入,所以我的猜测是最快的解决方案是lookup table引用数组的所有32个输出。优雅不会赢得积分。警告:air code

Function DoIt(ByVal Input As Long) As Long  
  Static lArray() As Long  
  Static bInitialised As Boolean   
  If Not bInitialised Then   
    ReDim Preserve lArray(0 To 31)   
    lArray(0) = 0   
    lArray(1) = &H80000000    
    lArray(2) = &HC0000000    
    ' etc... '  
    bInitialised = True 
  End If
  DoIt = lArray(Input)  ' for bonus marks raises an error on illegal input ' 
End Function  

如果你想要更通用的东西,VBSpeed对fast VB6 left-shifts的长期公开竞争。

  • 这是当前的赢家ShiftLeft04,它使用了一些可怕的,对不起我的意思是精彩,在VB6中获得内联汇编程序的技巧。你会笑,你会哭,你会恐怖地尖叫......
  • 目前的亚军ShiftLeft06约有200行全本地VB6。花费1.3倍,但仍然很快。

答案 2 :(得分:0)

我没有VB6,但这是我将如何在.Net

中完成的
    Const allBroadcast As Integer = Integer.MaxValue ' = 2,147,483,647
    Dim mask As Integer
    'three examples
    mask = allBroadcast << (32 - 24) '/24
    mask = allBroadcast << (32 - 16) '/16
    mask = allBroadcast << (32 - 8) '/8