Quantcast
Channel: Visual Basic 6.0 - Superior Source Code
Viewing all 181 articles
Browse latest View live

8085 MICROPROCESSOR SIMULATOR

$
0
0
The 8085 Microprocessor Simulator is a total software solution to replace the microprocessor kit from training and design labs. The Simulator executes the instructions from the user entered program, instruction by instruction showing all the register and flag status at the end of execution of each instruction. Microsoft Visual Basic is probably the fastest and easiest way to create applications for Microsoft Windows. Visual Basic provides you with a complete set of tools to simplify rapid application development.

Download from me


The 8085 is a complex IC of sequential circuits. The sequential circuits are designed to do some operation depending on what is the input on their lines. The vital inputs on the lines are what therefore determine what operation will be done by the sequential circuits inside it. The operations can be very complex and therefore this chip is also called a processor. Since we can find a way to put different values of inputs to the input lines of the processor at different times, we can make it execute different operations in a sequence that we desire. Thus, in other words we can make the processor execute a program to do useful things for us. These inputs then could alternately, be called instructions.


The program that we desire to be executed must be loaded into consecutive locations of memory chips. The memory is not part of the 8085 processor. The memory chips are again sequential circuits consisting of flip-flops that are capable of storing digital values. Since we would be interested in storing a huge number of such digital values, a large number of these memories are packed together with a scheme of addresses, so that we can address them individually. Generally the memories a rearranged in large numbers of 8 bit bunches each. The 8085 has a address bus which is 16 bit wide. Therefore it can put 2^16 different digital values on it, and therefore it can address a maximum of 2^16 different address locations. This is called the addressing space and it is 64 kilobyte for the 8085, because 2^16= 65535. And then we ask the processor to execute those instructions from a particular memory location on wards. It goes on executing those instructions one after another. The processor uses certain internal memory locations called Registers in doing all the operations that we ask it to do. The contents of those memory locations can be directly altered by the instructions that we give.


INTEL Corp. is generally recognized as the company that introduced the microprocessor successfully in the market. The first microprocessor, the 4004 was introduced in 1971.It was a central component in the chip set, called MCS-4.The microprocessors introduced between 1971 and 1973 were the first generation systems. They used PMOS technology, which provided low cost, slow speed and low output currents. After 1973-second generation microprocessors such as Motorola 6800 and 6809,Intel 8085 evolved. They were fabricated using NMOS technology. After 1978 The third generation microprocessors were evolved. They were 16 bit wide and included Intel 8086/80186/80286.They were designed using HMOS technology. In 1980 the fourth generation microprocessors evolved. Since 1985,32 bit microprocessors are fabricated using low power version of HMOS technology called HCMOS and they include an on-chip RAM called cache memory to speed up program execution. So extensive research is being carried out for the implementation of more on-chip functions and for the improvement of the speeds of memory and I/O devices. A machine language program consists of either binary or hexadecimal OP(operation)codes. Eight bit microcomputers can be programmed using machine language. A microprocessor has a unique set of machine language instructions defined by the manufacturer. No 2 microprocessors have same machine language instruction set.


Assembly Language

Assembly Language uses semi-English statements for 8 bit microprocessors. Each instruction in an assembly language comprises:(a) Label Field(b) Instruction, Mnemonic or Op-code field(c) Operand field(d) Assembly language basically consists of programs written with the help of mnemonics. Mnemonic is a combination of letters to suggest the operation of an instruction. In general an instruction has 2 components-operation code (OP-code) field and Address field.The OP-code field specifies how data is to be manipulated and the purpose of the address field is to indicate the address of a data item..

High- Level Language

Most 16 and 32 bit microprocessors in addition to assembly and machine language use a more understandable human oriented language called high-level language. High level language programs are composed of English language type statements .a no of high-level language.Regardless of what type of language is used to write a program, the microcomputers understand only binary numbers. So the programs must eventually be translated into their appropriate binary forms. An assembler is one such translator that translates a program written in assembly language to machine language (object code). A compiler/an interpreter converts a high-level language program into a machine language one. A compiler translates the entire source code to object code and then executes it. On the other hand, the interpreter performs line-by-line translation and execution simultaneously like FORTRAN, COBOL, BASIC, C, C++ are widely used these days.


DATA TRANSFER GROUPS

These groups include the move, exchange, load, and store operations. Data transfer instructions are among the most widely used of all microprocessor instructions. This group of instructions transfers data to and from registers and memory. None of the instructions of this group are the flag affecting instructions.The instructions included in this group are
 MOV, MVI, LXI, LDA, STA, LHLD, SHLD, LDAX, STAX, and XCHG 

For e.g.:MOV (A, B) will move the contents of register B to register A.


 ARITHEMATIC GROUPS

 This group includes the add, add with carry, subtract, subtract with borrow, increment, decrement, and decimal adjust accumulator operations. This group of instructions performs arithmetic operations on data in registers and memory. Unless indicated otherwise all the instructions are flag affecting instructions. All subtraction operations are performed via 2s complement arithmetic and set the carry flag to 1 to indicate a borrow and clear it to indicate no borrow.The instructions included in this group are ADD, ADC, SUB, SBB, DAD, INR, INX, DCR, DCX , and DAA. For e.g.:ADD B will add the contents of register B to the contents of register A and store the result in A. 

LOGICAL GROUPS

 This include AND, OR, XOR, compare, rotate and complement instructions. This group of instructions performs. Logical (Boolean) operations o the data in registers and memory and on flags.The instructions include in the group are
 ANA, XRA, ORA, CMP, AI, XRI, ORI,CPI, RLC, RRC, RAR, RAL, CMA, STC and CMC. For e.g.:ANA C will logically AND the contents of register C with the contents of register A and store the result in A. 


BRANCHING GROUPS

This include jump, call, return and restart instructions. This group of instructions alters the normal sequential program flow. The to types of branch instructions are:-Unconditional-Conditional. Unconditional transfers simply perform the specified operation o the program counter.Conditional transfers examine the status of one of the four MPU flags to determine whether the specified branch is to be executed.The instructions include in the group are Unconditional – 
 JMP, RET, CALL, RST 0, RST 1, RST 2, RST 3, RST 4,RST 5, RST 6, RST 7, PCHL. Conditional
- JNZ, JZ, JNC, JC, JPO, JPE, JP, JM, CNZ, CZ, CNC, CC,CPO, CPE, CP CM, RNZ, RZ, RNC, RC, RPO, RPE, RP, RM. For e.g.:JMP 4000 will transfer the program flow to the memory location 4000. 


STACK, I/O AND MACHINE CONTROL INSTRUCTIONS

 This include push and pop, input and output, exchange, interrupt enables and disables,no operation and halts, and multi – purpose read and set interrupt mask instructions.This group of instructions performs inputs and outputs, manipulates the stack, alters the internal control flags.The instructions included in the group are:Stack operations
 – 
 PUSH, POP, XTHL, and PCHL

Control operations.
 – 
 DI, EI, NOP, HLT, RIM, SIM 
Input/output operations

- OUT and IN 

For e.g.:PUSH B will push the contents the register B to the stack which is initialized previously.


THE 8085 SIMULATOR 

The 8085 Microprocessor Simulator is a total software solution to replace the microprocessor kit from training and design labs. The Simulator executes the instructions from the user entered program, instruction by instruction showing all the register and flag status at the end of execution of each instruction. The input process is fast and efficient, leading to better productivity. The Mnemonic Pad allows the user to enter the code. This makes is impossible to enter a wrong Mnemonic. The Tool tips tell you the syntax along with the operation performed by a particular Mnemonic. The Data Entry Window allows you to enter the Data Segment of your code. This is provided to enable the user to enter the data once and save it along with the code






Splines in VB6

$
0
0

Preview:


OptionExplicit
'
PublicTypeP_Type
XAsDouble' Coordinate x dei punti.
YAsDouble' Coordinate y dei punti.
'z As Double ' Coordinate z dei punti.
EndType
PublicSubBezier_C(Pi()AsP_Type,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva di Bezier calcolata
' al valore u (0 <= u <= 1). La curva e' calcolata in modo
' parametrico con il valore 0 di u corrispondente a Pc(0)
' ed il valore 1 corrispondente a Pc(NPC_1).
' Questo algoritmo ricalca la forma classica del polinomio
' di Bernstein.
'
DimI&,K&,NPI_1&,NPC_1&,NF&,u#,BF#
'
NPI_1=UBound(Pi)
NPC_1=UBound(Pc)
'NF = Prodotto(NPI_1)
'
ForI=0ToNPC_1
u=CDbl(I)/CDbl(NPC_1)
Pc(I).X=0#
Pc(I).Y=0#
'Pc(I).z = 0#
ForK=0ToNPI_1
'BF = NF * (u ^ K) * ((1 - u) ^ (NPI_1 - K)) _
/(Prodotto(K)*Prodotto(NPI_1-K))
BF=Prodotto(NPI_1,K+1)*(u^K)*((1#-u)^(NPI_1-K))_
/Prodotto(NPI_1-K)
Pc(I).X=Pc(I).X+Pi(K).X*BF
Pc(I).Y=Pc(I).Y+Pi(K).Y*BF
'Pc(I).z = Pc(I).z + Pi(K).z * BF
NextK
NextI
'
'
'
EndSub
PublicSubBezier_1(Pi()AsP_Type,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva di Bezier.
' La curva e' calcolata in modo parametrico (0 <= u < 1)
' con il valore 0 di u corrispondente a Pc(0);
' Attenzione: il punto Pc(NPC_1), corrispondente al valore u = 1,
' non puo' essere calcolato.
'
' Parametri:
' Pi(0 to NPI - 1): Vettore dei punti, dati, da
' approssimare.
' Pc(0 to NPC - 1): Vettore dei punti, calcolati,
' della curva approssimante.
'
DimI&,K&,NPI_1&,NPC_1&
Dimu#,u_1#,ue#,u_1e#,BF#
'
NPI_1=UBound(Pi)' N. di punti da approssimare - 1.
NPC_1=UBound(Pc)' N. di punti sulla curva - 1.
'
' La curva inizia sempre da Pi(0) -> u = 0:
Pc(0).X=Pi(0).X
Pc(0).Y=Pi(0).Y
'Pc(0).z = Pi(0).z
'
ForI=1ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
ue=1#
u_1=1#-u
u_1e=u_1^NPI_1
'
Pc(I).X=0#
Pc(I).Y=0#
'Pc(I).z = 0#
ForK=0ToNPI_1
BF=Prodotto(NPI_1,K+1)*ue*u_1e/Prodotto(NPI_1-K)
Pc(I).X=Pc(I).X+Pi(K).X*BF
Pc(I).Y=Pc(I).Y+Pi(K).Y*BF
'Pc(I).z = Pc(I).z + Pi(K).z * BF
'
ue=ue*u
u_1e=u_1e/u_1
NextK
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'Pc(NPC_1).z = Pi(NPI_1).z
'
'
'
EndSub
PublicSubBezier(Pi()AsP_Type,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva di Bezier.
' La curva e' calcolata in modo parametrico (0 <= u < 1)
' con il valore 0 di u corrispondente a Pc(0);
'
' Questa versione elimina alcuni problemi di "underflow"
' e di "overflow" presentati dalla Bezier_1 e dalla Bezier_C.
'
' Parametri:
' Pi(0 to NPI - 1): Vettore dei punti, dati, da
' approssimare.
' Pc(0 to NPC - 1): Vettore dei punti, calcolati,
' della curva approssimante.
'
DimI&,K&,NPI_1&,NPC_1&
Dimu#,u_1#,ue#,BF#
StaticNPI_1_O&,CB_Tav#()
'
NPI_1=UBound(Pi)' N. di punti da approssimare - 1 (deve essere 2 <= NPI_1 <= 1029).
NPC_1=UBound(Pc)' N. di punti sulla curva - 1.
'
IfNPI_1_O<>NPI_1Then
' Prepara la tavola dei coefficienti binomiali:
ReDimCB_Tav#(0ToNPI_1)
ForK=0ToNPI_1
CB_Tav(K)=rncr(NPI_1,K)
NextK
'
NPI_1_O=NPI_1
EndIf
'
' La curva inizia sempre da Pi(0) -> u = 0:
Pc(0).X=Pi(0).X
Pc(0).Y=Pi(0).Y
'Pc(0).z = Pi(0).z
'
ForI=1ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
ue=1#
u_1=1#-u
'
Pc(I).X=0#
Pc(I).Y=0#
'Pc(I).z = 0#
ForK=0ToNPI_1
BF=CB_Tav(K)*ue*u_1^(NPI_1-K)
'
Pc(I).X=Pc(I).X+Pi(K).X*BF
Pc(I).Y=Pc(I).Y+Pi(K).Y*BF
'Pc(I).z = Pc(I).z + Pi(K).z * BF
'
ue=ue*u
NextK
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'Pc(NPC_1).z = Pi(NPI_1).z
'
'
'
EndSub
PublicSubBezier_P(Pi()AsP_Type,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva di Bezier calcolata
' al valore u (0 <= u < 1). La curva e' calcolata in modo
' parametrico con il valore 0 di u corrispondente a Pc(0);
' Attenzione: il punto Pc(NPC_1), corrispondente al valore u = 1,
' non puo' essere calcolato.
'
' Questo algoritmo (tratto da una pubblicazione di P. Bourke
' e tradotto dal C) e' particolarmente interessante, in quanto
' evita l' uso dei fattoriali della forma normale.
'
DimK&,I&,KN&,NPI_1&,NPC_1&,NN&,NKN&
Dimu#,uk#,unk#,Blend#
'
NPI_1=UBound(Pi)
NPC_1=UBound(Pc)
'
ForI=0ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
uk=1#
unk=(1#-u)^NPI_1
'
Pc(I).X=0#
Pc(I).Y=0#
'Pc(I).z = 0#
'
ForK=0ToNPI_1
NN=NPI_1
KN=K
NKN=NPI_1-K
Blend=uk*unk
uk=uk*u
unk=unk/(1#-u)
DoWhileNN>=1
Blend=Blend*CDbl(NN)
NN=NN-1
IfKN>1Then
Blend=Blend/CDbl(KN)
KN=KN-1
EndIf
IfNKN>1Then
Blend=Blend/CDbl(NKN)
NKN=NKN-1
EndIf
Loop
'
Pc(I).X=Pc(I).X+Pi(K).X*Blend
Pc(I).Y=Pc(I).Y+Pi(K).Y*Blend
'Pc(I).z = Pc(I).z + Pi(K).z * Blend
NextK
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'Pc(NPC_1).z = Pi(NPI_1).z
'
'
'
EndSub
PrivateFunctionProdotto(ByValN2&,OptionalByValN1&=2)AsDouble
'
' Ritorna il prodotto dei numeri, consecutivi, interi e positivi,
' da N1 a N2 (0 < N1 <= N2). Se N1 > N2 ritorna 1.
' Se N1 manca, ritorna il Fattoriale di N2; in questo caso puo'
' anche essere N2 = 0 perche', per definizione, e' 0! = 1:
'
DimPr#,I&
'
Pr=1#
ForI=N1ToN2
Pr=Pr*CDbl(I)
NextI
'
Prodotto=Pr
'
'
'
EndFunction
PublicSubB_Spline(Pi()AsP_Type,ByValNK&,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva B-Spline.
' La curva e' calcolata in modo parametrico (0 <= u <= 1)
' con il valore 0 di u corrispondente a Pc(0) ed il valore
' 1 corrispondente a Pc(NPC_1).
'
' Parametri:
' Pi(0 to NPI - 1): Vettore dei punti, dati, da
' approssimare.
' Pc(0 to NPC - 1): Vettore dei punti, calcolati,
' della curva approssimante.
' NK: Numero di nodi della curva
' approssimante:
' NK = 2 -> segmenti di retta.
' NK = 3 -> curve quadratiche.
' .. . ..................
' NK = NPI -> splines di Bezier.

DimNPI_1&,NPC_1&,I&,J&,tmax#,u#,ut#,bn#()
ConstEps=0.0000001
'
NPI_1=UBound(Pi)' N. di punti da approssimare - 1.
NPC_1=UBound(Pc)' N. di punti sulla curva - 1.
tmax=NPI_1-NK+2
'
' La curva inizia sempre da Pi(0) -> u = 0:
Pc(0).X=Pi(0).X
Pc(0).Y=Pi(0).Y
'
ForI=1ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
ut=u*tmax
IfAbs(ut-CDbl(NPI_1+NK-2))<=EpsThen
Pc(I).X=Pi(NPI_1).X
Pc(I).Y=Pi(NPI_1).Y
Else
CallB_Basis(NPI_1,ut,NK,bn())
Pc(I).X=0#
Pc(I).Y=0#
ForJ=0ToNPI_1
Pc(I).X=Pc(I).X+bn(J)*Pi(J).X
Pc(I).Y=Pc(I).Y+bn(J)*Pi(J).Y
NextJ
EndIf
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'
'
'
EndSub
PrivateSubB_Basis(ByValNPI_1&,ByValut#,ByValK&,bn#())
'
' Compute the basis function (also called weight)
' for the B-Spline approximation curve:
'
DimNT&,I&,J&
Dimb0#,b1#,bl0#,bl1#,bu0#,bu1#
ReDimbn#(0ToNPI_1+1),bn0#(0ToNPI_1+1),t#(0ToNPI_1+K+1)
'
NT=NPI_1+K+1
ForI=0ToNT
If(I<K)Thent(I)=0#
If((I>=K)And(I<=NPI_1))Thent(I)=CDbl(I-K+1)
If(I>NPI_1)Thent(I)=CDbl(NPI_1-K+2)
NextI
ForI=0ToNPI_1
bn0(I)=0#
If((ut>=t(I))And(ut<t(I+1)))Thenbn0(I)=1#
If((t(I)=0#)And(t(I+1)=0#))Thenbn0(I)=0#
NextI
'
ForJ=2ToK
ForI=0ToNPI_1
bu0=(ut-t(I))*bn0(I)
bl0=t(I+J-1)-t(I)
If(bl0=0#)Then
b0=0#
Else
b0=bu0/bl0
EndIf
bu1=(t(I+J)-ut)*bn0(I+1)
bl1=t(I+J)-t(I+1)
If(bl1=0#)Then
b1=0#
Else
b1=bu1/bl1
EndIf
bn(I)=b0+b1
NextI
ForI=0ToNPI_1
bn0(I)=bn(I)
NextI
NextJ
'
'
'
EndSub
PublicSubC_Spline(Pi()AsP_Type,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva C-Spline.
' La curva e' calcolata in modo parametrico (0 <= u <= 1)
' con il valore 0 di u corrispondente a Pc(0) ed il valore
' 1 corrispondente a Pc(NPC_1).
'
' Parametri:
' Pi(0 to NPI - 1): Vettore dei punti, dati, da
' interpolare.
' Pc(0 to NPC - 1): Vettore dei punti, calcolati,
' della curva interpolante.
'
DimNPI_1&,NPC_1&,I&,J&
Dimu#,ui#,uui#
Dimcof()AsP_Type
'
NPI_1=UBound(Pi)' N. di punti da interpolare - 1.
NPC_1=UBound(Pc)' N. di punti sulla curva - 1.
'
CallFind_CCof(Pi(),NPI_1+1,cof())
'
' La curva inizia sempre da Pi(0) -> u = 0:
Pc(0).X=Pi(0).X
Pc(0).Y=Pi(0).Y
'
ForI=1ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
J=Int(u*CDbl(NPI_1))+1
If(J>(NPI_1))ThenJ=NPI_1
'
ui=CDbl(J-1)/CDbl(NPI_1)
uui=u-ui
'
Pc(I).X=cof(4,J).X*uui^3+cof(3,J).X*uui^2+cof(2,J).X*uui+cof(1,J).X
Pc(I).Y=cof(4,J).Y*uui^3+cof(3,J).Y*uui^2+cof(2,J).Y*uui+cof(1,J).Y
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'
'
'
EndSub
PrivateFunctionrncr(ByValN&,ByValK&)AsDouble
'
' Calcola i coefficienti binomiali Cn,k come:
' rncr = N! / (K! * (N - K)!)
'
' Nota: La funzione ha senso solo per 0 < N, K <= N
' e 0 <= K. Nessun errore viene segnalato.
'
DimI&,rncr_T#
'
If((N<1)Or(K<1)Or(N=K))Then
rncr=1#
'
Else
rncr_T=1#
ForI=1ToN-K
rncr_T=rncr_T*(1#+CDbl(K)/CDbl(I))
NextI
'
rncr=rncr_T
EndIf
'
'
'
EndFunction
PublicSubT_Spline(Pi()AsP_Type,ByValVZ&,Pc()AsP_Type)
'
' Ritorna, nel vettore Pc(), i valori della curva T-Spline.
' La curva e' calcolata in modo parametrico (0 <= u <= 1)
' con il valore 0 di u corrispondente a Pc(0) ed il valore
' 1 corrispondente a Pc(NPC_1).
'
' Parametri:
' Pi(0 to NPI - 1): Vettore dei punti, dati, da
' interpolare.
' Pc(0 to NPC - 1): Vettore dei punti, calcolati,
' della curva interpolante.
' VZ: Valore di tensione della curva
' (1 <= VZ <= 100): valori grandi
' di VZ appiattiscono la curva.
'
DimNPI_1&,NPC_1&,I&,J&
DimH#,z#,z2i#,szh#,u#,u0#,u1#,du1#,du0#
Dims()AsP_Type
'
NPI_1=UBound(Pi)' N. di punti da interpolare - 1.
NPC_1=UBound(Pc)' N. di punti sulla curva - 1.
z=CDbl(VZ)
'
CallFind_TCof(Pi(),NPI_1+1,s(),z)
'
' La curva inizia sempre da Pi(0) -> u = 0:
Pc(0).X=Pi(0).X
Pc(0).Y=Pi(0).Y
'
H=1#/CDbl(NPI_1)
szh=Sinh(z*H)
z2i=1#/z/z
ForI=1ToNPC_1-1
u=CDbl(I)/CDbl(NPC_1)
J=Int(u*CDbl(NPI_1))+1
If(J>(NPI_1))ThenJ=NPI_1
'
u0=CDbl(J-1)/CDbl(NPI_1)
u1=CDbl(J)/CDbl(NPI_1)
du1=u1-u
du0=u-u0
'
Pc(I).X=s(J).X*z2i*Sinh(z*du1)/szh+(Pi(J-1).X-s(J).X*z2i)*du1/H
Pc(I).X=Pc(I).X+s(J+1).X*z2i*Sinh(z*du0)/szh+(Pi(J).X-s(J+1).X*z2i)*du0/H

Pc(I).Y=s(J).Y*z2i*Sinh(z*du1)/szh+(Pi(J-1).Y-s(J).Y*z2i)*du1/H
Pc(I).Y=Pc(I).Y+s(J+1).Y*z2i*Sinh(z*du0)/szh+(Pi(J).Y-s(J+1).Y*z2i)*du0/H
NextI
'
' La curva finisce sempre su Pi(NPI_1) -> u = 1:
Pc(NPC_1).X=Pi(NPI_1).X
Pc(NPC_1).Y=Pi(NPI_1).Y
'
'
'
EndSub
PrivateSubFind_TCof(Pi()AsP_Type,ByValNPI&,s()AsP_Type,ByValz#)
'
' Find the coefficients of the T-Spline
' using constant interval:
'
DimI&,H#,a0#,b0#,zh#,z2#
'
ReDims(1ToNPI)AsP_Type,f(1ToNPI)AsP_Type
ReDima(1ToNPI)AsDouble,B(1ToNPI)AsDouble,C(1ToNPI)AsDouble
'
H=1#/CDbl(NPI-1)
zh=z*H
a0=1#/H-z/Sinh(zh)
b0=z*2#*Cosh(zh)/Sinh(zh)-2#/H
ForI=1ToNPI-2
a(I)=a0
B(I)=b0
C(I)=a0
NextI
'
z2=z*z/H
ForI=1ToNPI-2
f(I).X=(Pi(I+1).X-2#*Pi(I).X+Pi(I-1).X)*z2
f(I).Y=(Pi(I+1).Y-2#*Pi(I).Y+Pi(I-1).Y)*z2
NextI
'
CallTRIDAG(a(),B(),C(),f(),s(),NPI-2)
ForI=1ToNPI-2
s(NPI-I).X=s(NPI-1-I).X
s(NPI-I).Y=s(NPI-1-I).Y
NextI
'
s(1).X=0#
s(NPI).X=0#
s(1).Y=0#
s(NPI).Y=0#
'
'
'
EndSub
PrivateSubFind_CCof(Pi()AsP_Type,ByValNPI&,cof()AsP_Type)
'
' Find the coefficients of the cubic spline
' using constant interval parameterization:
'
DimI&,H#
'
ReDims(1ToNPI)AsP_Type,f(1ToNPI)AsP_Type,cof(1To4,1ToNPI)AsP_Type
ReDima(1ToNPI)AsDouble,B(1ToNPI)AsDouble,C(1ToNPI)AsDouble
'
H=1#/CDbl(NPI-1)
ForI=1ToNPI-2
a(I)=1#
B(I)=4#
C(I)=1#
NextI
'
ForI=1ToNPI-2
f(I).X=6#*(Pi(I+1).X-2#*Pi(I).X+Pi(I-1).X)/H/H
f(I).Y=6#*(Pi(I+1).Y-2#*Pi(I).Y+Pi(I-1).Y)/H/H
NextI
'
CallTRIDAG(a(),B(),C(),f(),s(),NPI-2)
ForI=1ToNPI-2
s(NPI-I).X=s(NPI-1-I).X
s(NPI-I).Y=s(NPI-1-I).Y
NextI
'
s(1).X=0#
s(NPI).X=0#
s(1).Y=0#
s(NPI).Y=0#
ForI=1ToNPI-1
cof(4,I).X=(s(I+1).X-s(I).X)/6#/H
cof(4,I).Y=(s(I+1).Y-s(I).Y)/6#/H
cof(3,I).X=s(I).X/2#
cof(3,I).Y=s(I).Y/2#
cof(2,I).X=(Pi(I).X-Pi(I-1).X)/H-(2#*s(I).X+s(I+1).X)*H/6#
cof(2,I).Y=(Pi(I).Y-Pi(I-1).Y)/H-(2#*s(I).Y+s(I+1).Y)*H/6#
cof(1,I).X=Pi(I-1).X
cof(1,I).Y=Pi(I-1).Y
NextI
'
'
'
EndSub
PrivateSubTRIDAG(a#(),B#(),C#(),f()AsP_Type,s()AsP_Type,ByValNPI_2&)
'
' Solves the tridiagonal linear system of equations:
'
DimJ&,bet#
ReDimgam#(1ToNPI_2)
'
IfB(1)=0ThenExitSub
'
bet=B(1)
s(1).X=f(1).X/bet
s(1).Y=f(1).Y/bet
ForJ=2ToNPI_2
gam(J)=C(J-1)/bet
bet=B(J)-a(J)*gam(J)
If(bet=0)ThenExitSub
s(J).X=(f(J).X-a(J)*s(J-1).X)/bet
s(J).Y=(f(J).Y-a(J)*s(J-1).Y)/bet
NextJ
'
ForJ=NPI_2-1To1Step-1
s(J).X=s(J).X-gam(J+1)*s(J+1).X
s(J).Y=s(J).Y-gam(J+1)*s(J+1).Y
NextJ
'
'
'
EndSub
PrivateFunctionCosh(ByValzAsDouble)AsDouble
'
' Ritorna il coseno iperbolico di z#:
'
Cosh=(Exp(z)+Exp(-z))/2#
'
'
'
EndFunction
PrivateFunctionSinh(ByValzAsDouble)AsDouble
'
' Ritorna il seno iperbolico di z#:
'
Sinh=(Exp(z)-Exp(-z))/2#
'
'
'
EndFunction

Syntax Highlighting Control in VB6

$
0
0
You can change the Deafult syntax colors of this control by its properties in design time, or in coding style. Space surrounding each word is significant. It allows searching on whole words. Note that these constant declares are long and could reach the line length limit of 1023 characters. If so, simply split to 2 constants and combine into a third constant with the appropriate name.

Download from me








Microsoft pig ignorance !

$
0
0

As I recover from a gruelling contract where I had to program in 4 different languages .. PIC Basic, C++, Javascript, & you guessed it, VB6 (my choice for post processing), I have come back here to see if there was any good news. Apparently not. Microsoft's stubbornness has not abated.
I saw a video recently that said "if you have an iphone, you can track your cycles at the click of a button. I believe there is an android app for that too; and if you have a Windows phone, I guess you can use it to carve the numbers into a rock". And that about sums up where MS has gone.
In my new environment, I am surrounded by people who use either a Mac or, reluctantly, Win 7. They apologise profusely if I must use W10. (To be fair, W10 is okay if you don't mind having to use Cortana to find your programs, to sign into everything, and can put up with daily changes because you can't turn off automatic updates (except on specific networks which is fine if you don't move). Microsoft is the epitome of success breeds contempt. It is becoming irrelevant. Dot Net itself is poopooed by developers and is fast becoming a second rate dead end.
There are career programmers who don't mind pounding the shift key putting squiggly brackets and parenthesis eveywhere until their code looks like Egyptian hieroglyphs, and then having to decipher gobbledygook errors when they forget the ";" at the end of a line or, god-forbid, use incorrect case. This is a careerist's gravy -- as much as doctors & lawyers invented a new language and writing style to obscure their methods and protect their industry, so it would seem the career programmers hide the simple behind jargon and layers of bloatware, text only IDEs, separate compilers, linkers and GUI builders.
Then there are those who just want to get the job done, to not have to wait a minute for compilation or a day installing a new framework, to use a powerful but simple "app" to produce a scripted equivalent of a spreadsheet. That's what VB6 is (not forgetting that VB6 is indeed the core of the scripting language in Excel). Someone invented VB, perfected VB6, then someone else came along and trashed it because it didn't fit the fashionable hieroglyphs and bloatware mantra. And along with it, our faith in them died. Currently, my W7 still makes a good desktop, but I am looking at Mint as Linux is now better supported by the open source community. For anything else, I use a Linux box or no OS. RIP MS.
Microsoft seemed to be suffering from a strain of collective pyromania, obsoleting stuff for fun, then hiding it behind patents and legalese to ensure no one can replicate what they have done (let's just remind ourselves that open source and Linux exists largely to escape the patent trolls). This is commercial bulimia. Dine well, engorge your coffers, then throw it all up again. Repeat until dead.
We have a clinical term for this disorder where I come from.. It's called pig ignorance.
A comment by



Http Recon Security Scanner – Advanced Web Server Fingerprinting

$
0
0

Introduction

HTTP Recon is an advanced web server fingerprinting system made in Visual Basic 6.0. We are accustomed to advanced VB6 projects, however, few are open source and most of them are sold for impressive amounts of money. Here we have to thank a security engineer named Marc Ruef. The httprecon project is doing some research in the field of web server fingerprinting, also known as http fingerprinting. The goal is the highly accurate identification of given httpd implementations. This is very important within professional vulnerability analysis.
Besides the discussion of different approaches and the documentation of gathered results also an implementation for automated analysis is provided. This software shall improve the easyness and efficiency of this kind of enumeration. Traditional approaches as like banner-grabbing, status code enumeration and header ordering analysis are used. However, many other analysis techniques were introduced to increase the possibilities of accurate web server fingerprinting. Some of them were already discussed in the book Die Kunst des Penetration Testing (Chapter 9.3, HTTP-Fingerprinting, pp. 530-550).



Here is the source code:

Flow

The application works very straight forward. After the user has defined the target service which shall be fingerprinted, a common tcp connection is opened to the destination port. If the connection could be established, the http requests are sent to the target service. This one will shall react with responses. These could be dissected to identify some specific fingerprint elements. Those elements are looked up in the local fingerprint database. If there is a match, the according implementation is flagged as "identified". All these flags were counted so httprecon is able to determine which implementation has the best match rate.

Architecture

The following picture illustrates the architecture of the whole framework. The scan engine uses nine different requests which are sent to the target web server. These shall provoke the response which can be used for the fingerprinting. There were different kind of requests used. Some of them are very common and legitimate (e.g. GET / HTTP/1.1) and others are usually not accepted due to their malicious nature (e.g. a very long URI in a GET request).

The dissection of the responses is handled by the parsing and fingerprint engine. As you can see many different fingerprint elements are looked up (e.g. statuscode, banner, Etag length, header-order, etc.). These elements are saved in the local fingerprint database which allows the sum of the matches. All data is correlated which will result in the final fingerprint scan report.

Features

These are the main features of the current implementation of httprecon which makes this solution better than other tools of this kind:
  • Many test-cases: There are nine test-cases possible
  • HTTPS/SSL support: Secure web servers can be tested too
  • Advanced result analysis: Different methods for the analysis of results is provided
  • Many fingerprint details: The analysis is based on many fingerprint elements
  • Plaintext Database: The fingerprint data is saved in a file-based plaintext database
  • Fingerprint Wizard: Fingerprints can be saved and updated within the GUI
  • IDS evasion mechanism: The configuration settings allow to use IDS evasion mechanisms
  • Reporting: XML, HTML and TXT reporting is provided for professional testers
  • Autoupdate: An autoupdate feature informs about new releases
  • Open-source (GPLv3): Everyone can improve the application for themselves
There are differen applications for http fingerprinting available. This Excel sheet is comparing the four most popular HTTP fingerprinting tools (httprecon, httprint, hmap, and WebserverFP).

Key Analysis Index

Most web server implementations come with a Key Analysis Index (KAI), a very special and dominant behaviour which allows a very quick identification. The following list shall demonstrate the KAI for some popular implementations:
  • Apache: Every generation of Apache web servers usually introduces these three values first in an http response header: Date, Server, and X-Powered-By (optional). The length of the ETag values varies between 17 and 34 bytes and they are usually surrounded by double-quotes. It is very typical for an Apache installation to announce PHP/x.x.x within the X-Powered-By line (it is also common for Abyss). It is also common that an Apache web server reacts with the statuscode 403 (Forbidden) if a very long URI was proposed within the request. Usually the supported http methods are announced as: GET, HEAD, POST, OPTIONS, and TRACE.
  • Microsoft IIS: The length of the ETag values varies between 18 and 23 bytes. This web server is the only one so far which is announcing ASP.NET within the X-Powered-By line.
  • Oracle Application Server: The length of the ETag values varies between 15 and 30 bytes and they are usually surrounded by double-quotes. Usually the supported http methods are announced as: OPTIONS, TRACE, GET, and HEAD. In some cases also an additional line similar to Allow is used and defined as Public.
  • Sun One Web Server: The implemenation by Sun Microsystems Inc. usually starts with the values Server, {Date|Content-type}.
  • Netscape Enterprise Server: This implementation usually uses these three values within a response header: Server, Date, and Content-type.
  • Compaq HTTP Server: Old implementations of the generation 5.x always propose HTTP/1.0 instead of HTTP/1.1 as protocol. A very special behaviour is the statustext "Ok" instead of full capitalized "OK" for a successful processing. They also use uncapitalized letters is a response line uses some dash (e.g. Content-type and Content-length). And the response header always consists of: Date, Server, Content-type, Content-length, and Set-Cookie. A Compaq HTTP Server sends the http statuscode 200 (Ok) even a very long URI was proposed within the request (also common for LANCOM DSL router).
  • Zyxel: The embedded web server of Zyxel devices proposes usually the same http response header structure: Content-Type, Date, Pragma, Expires, Transfer-Encoding, Server, and EXT. Very special in this case is the header line EXT.
  • 4D WebSTAR: Versions prior 4.x always announce the MIME-Version as first element of the http response header. The version 4.x do not use this value anymore and rely on Server as first element. And in the later releases 5.x the Date announcement moved the Server announcement to the second line. A request for a non-existing ressource returns the statuscode "File Not Found" instead of the more common "Not Found".
  • Roxen: The length of the ETag values is always set to 34 bytes and they are usually surrounded by double-quotes.
  • OmniHTTPd: Another special behaviour for successful requests is the status text "Document Follows" (similar to TclHttpd) where usually an "OK" is used. The response headers usually contain the values Content-Length, Content-Type, Date and the header is ended by the value Server.
  • TclHttpd: Another special behaviour for successful requests is the status text "Data follows" (similar to OmniHTTPd) where usually an "OK" is used.
  • Gatling: A very special behaviour for successful requests is the status text "Coming Up" where usually an "OK" is used.
  • Squid: Common http get requests always produce the announcement of HTTP/1.0 instead of HTTP/1.1 as protocol.

Counter-measures

The possibility of fingerprinting is not a vulnerability in a traditional way which allows to compromise a host. It is more a flaw or exposure which may provide the foundation for further enumeration and specific attack scenarios.

Nevertheless, applying some counter-measures to harden a service is always a good idea. Preventing fingerprinting 100 % is not possible due to the nature of interaction between network software. But there are possibilities to decrease the accuracy of such an analysis. These are illustrated in the diagram and listed below:

Change or supression of banner

The most accepted and widely known approach to defend against fingerprinting is the manipulation or change of the application banner. Within web responses the line Server announces the name of the given implementation. Some web servers allow the change of this value within a configuration file.
Apache supports downstripping the announcement with the ServerToken directive. Downstripping requires the definition of Prod which would announce "Apache" only (see the ServerSignature directive too). To change this value really some manipulation of the file /src/include/httpd.h within the source-code (AP_SERVER_BASEVENDOR, AP_SERVER_BASEPRODUCT, AP_SERVER_MAJORVERSION_NUMBER, AP_SERVER_MINORVERSION_NUMBER, AP_SERVER_PATCHLEVEL_NUMBER) is required:
* The below defines the base string of the Server: header. Additional
* tokens can be added via the ap_add_version_component() API call.
*
* The tokens are listed in order of their significance for identifying the
* application.
*
* "Product tokens should be short and to the point -- use of them for
* advertizing or other non-essential information is explicitly forbidden."
*
* Example: "Apache/1.1.0 MrWidget/0.1-alpha"
*/
#define AP_SERVER_BASEVENDOR "Apache Software Foundation"
#define AP_SERVER_BASEPROJECT "Apache HTTP Server"
#define AP_SERVER_BASEPRODUCT "Apache"

#define AP_SERVER_MAJORVERSION_NUMBER 2
#define AP_SERVER_MINORVERSION_NUMBER 2
#define AP_SERVER_PATCHLEVEL_NUMBER 6
#define AP_SERVER_DEVBUILD_BOOLEAN 0

#if AP_SERVER_DEVBUILD_BOOLEAN
#define AP_SERVER_ADD_STRING "-dev"
#else
#define AP_SERVER_ADD_STRING ""
#endif
Microsoft IIS requires some hex hack in the library W3SVC.DLL to change the Server-output. There is a freeware named MS IIS/PWS Banner Edit Tool available which automates this manipulation. IISBanner is a well-known ISAPI filter which can be used to safely remove or disguise the IIS server header by editing the INI file. Microsoft suggests the use of URLscan which introduces the same advantages.
thttpd allows some minor changes within the file config.h which steers some of the settings during compilation (e.g. ERR_APPEND_SERVER_INFO for the announcement of the server name within server generated error pages or the default charset of iso-8859-1 in DEFAULT_CHARSET). Furthermore it is possible to change SHOW_SERVER_VERSION which suppresses the version number announcement in the Server line. To change or suppress the real server name a modification of EXPOSED_SERVER_SOFTWARE within libhttpd.c is required:
#define EXPOSED_SERVER_SOFTWARE SERVER_SOFTWARE
#else /* SHOW_SERVER_VERSION */
#define EXPOSED_SERVER_SOFTWARE "thttpd"
#endif /* SHOW_SERVER_VERSION */
The open-source web server fnord does not support any configuration settings or constant mutation within the source code to modify the application behavior easily. The announcement of the web server as FNORD is realized within the separated replies created by buffer_puts() in httpd.c. This includes the application banner, status messages and header order. However, enhanced search and replace modifications might improve the obscurity without touching the architecture of the application. Further improvements as like introduction of new http methods (by default only GET, POST and HEAD are suppoted in version 1.10) require some deeper modifications.
Some modules (e.g. PHP and SSH) announce themselves within the Server line. In most cases this can be prevented with a configuration setting for the according module. For PHP in the file php.ini the value expose_php must be set to Off.

Change statuscode and statustext

Web servers include implementation dependent statuscodes and statustexts in their responses. Changeing them prevents most of todays web server fingerprinting. Only a few http daemons allow such change of basic behaviour within run-time configuration.
Apache requires some changes within the source code and re-compilation. In /src/include/httpd.h the statuscodes are defined as integer constants:
* The size of the static array in http_protocol.c for storing
* all of the potential response status-lines (a sparse table).
* A future version should dynamically generate the apr_table_t at startup.
*/
#define RESPONSE_CODES 57

#define HTTP_CONTINUE 100
#define HTTP_SWITCHING_PROTOCOLS 101
#define HTTP_PROCESSING 102
#define HTTP_OK 200
#define HTTP_CREATED 201
#define HTTP_ACCEPTED 202
#define HTTP_NON_AUTHORITATIVE 203
#define HTTP_NO_CONTENT 204
#define HTTP_RESET_CONTENT 205
#define HTTP_PARTIAL_CONTENT 206
#define HTTP_MULTI_STATUS 207
#define HTTP_MULTIPLE_CHOICES 300
#define HTTP_MOVED_PERMANENTLY 301
#define HTTP_MOVED_TEMPORARILY 302
#define HTTP_SEE_OTHER 303
#define HTTP_NOT_MODIFIED 304
#define HTTP_USE_PROXY 305
#define HTTP_TEMPORARY_REDIRECT 307
#define HTTP_BAD_REQUEST 400
#define HTTP_UNAUTHORIZED 401
#define HTTP_PAYMENT_REQUIRED 402
#define HTTP_FORBIDDEN 403
#define HTTP_NOT_FOUND 404
#define HTTP_METHOD_NOT_ALLOWED 405
#define HTTP_NOT_ACCEPTABLE 406
#define HTTP_PROXY_AUTHENTICATION_REQUIRED 407
#define HTTP_REQUEST_TIME_OUT 408
#define HTTP_CONFLICT 409
#define HTTP_GONE 410
#define HTTP_LENGTH_REQUIRED 411
#define HTTP_PRECONDITION_FAILED 412
#define HTTP_REQUEST_ENTITY_TOO_LARGE 413
#define HTTP_REQUEST_URI_TOO_LARGE 414
#define HTTP_UNSUPPORTED_MEDIA_TYPE 415
#define HTTP_RANGE_NOT_SATISFIABLE 416
#define HTTP_EXPECTATION_FAILED 417
#define HTTP_UNPROCESSABLE_ENTITY 422
#define HTTP_LOCKED 423
#define HTTP_FAILED_DEPENDENCY 424
#define HTTP_UPGRADE_REQUIRED 426
#define HTTP_INTERNAL_SERVER_ERROR 500
#define HTTP_NOT_IMPLEMENTED 501
#define HTTP_BAD_GATEWAY 502
#define HTTP_SERVICE_UNAVAILABLE 503
#define HTTP_GATEWAY_TIME_OUT 504
#define HTTP_VERSION_NOT_SUPPORTED 505
#define HTTP_VARIANT_ALSO_VARIES 506
#define HTTP_INSUFFICIENT_STORAGE 507
#define HTTP_NOT_EXTENDED 510
And in /src/modules/http/http_protocol.c the statustexts are defined as string constants:
#else
static const char * const status_lines[RESPONSE_CODES] =
#endif
{
"100 Continue",
"101 Switching Protocols",
"102 Processing",
#define LEVEL_200 3
"200 OK",
"201 Created",
"202 Accepted",
"203 Non-Authoritative Information",
"204 No Content",
"205 Reset Content",
"206 Partial Content",
"207 Multi-Status",
#define LEVEL_300 11
"300 Multiple Choices",
"301 Moved Permanently",
"302 Found",
"303 See Other",
"304 Not Modified",
"305 Use Proxy",
"306 unused",
"307 Temporary Redirect",
#define LEVEL_400 19
"400 Bad Request",
"401 Authorization Required",
"402 Payment Required",
"403 Forbidden",
"404 Not Found",
"405 Method Not Allowed",
"406 Not Acceptable",
"407 Proxy Authentication Required",
"408 Request Time-out",
"409 Conflict",
"410 Gone",
"411 Length Required",
"412 Precondition Failed",
"413 Request Entity Too Large",
"414 Request-URI Too Large",
"415 Unsupported Media Type",
"416 Requested Range Not Satisfiable",
"417 Expectation Failed",
"418 unused",
"419 unused",
"420 unused",
"421 unused",
"422 Unprocessable Entity",
"423 Locked",
"424 Failed Dependency",
/* This is a hack, but it is required for ap_index_of_response
* to work with 426.
*/
"425 No code",
"426 Upgrade Required",
#define LEVEL_500 46
"500 Internal Server Error",
"501 Method Not Implemented",
"502 Bad Gateway",
"503 Service Temporarily Unavailable",
"504 Gateway Time-out",
"505 HTTP Version Not Supported",
"506 Variant Also Negotiates",
"507 Insufficient Storage",
"508 unused",
"509 unused",
"510 Not Extended"
};
An easier way to change the status reaction for specific request types (e.g. unsupported http methods as like DELETE) is the use of re-write rules. Instead of react with the expected error message 405 a less usefull forwarding to a 404 error site is possible. Most web servers support such definitions within .htaccess files. The following example is redirecting the unwanted requests to 403 Forbidden instead to 405 Method Not Allowed if the Apache web server has mod_rewrite enabled:
RewriteRule .* - [F]

Change header-values and order

Some web server fingerprinting tools regard header values and header order. Changeing this within the web server usually requires some deep impact to the source code too. This requires a very high level of understanding the given application. The rate of errors might be very high with such an intrusive change.
In Microsoft IIS new custom header values can be added which changes the overview fingerprint of the header order. Just by adding one new header line (usually web browsers ignore those which start with X, e.g. X-Garbage) the possibilities of successful fingerprints can be reduced. This is possible very easily in the tab HTTP headers in the web site properties. Those can be reached within the context menu of the according web site in the Internet Information Services (IIS) Manager. In some cases it is possible to overwrite some other header values (e.g. the location in 302 moved messages). However, this is not possible for the Server banner itself.
Add Custom HTTP Header in MS IIS
However, some scripting languages as like PHP allow the web developer to have some influence to the headers with the function header(). For example a new header with the call header("X-Powered-By: ASP.NET 2.0") can be used althought no ASP.NET is used at all. This compromises the fingerprint analysis, especially if it is very static and pattern-based, in any way. In ASP.NET the function Response.AppendHeader() is used for the same purposes.
And in JSP different methods of the response object defined by the javax.servlet.http.HttpServletResponse interface might be used: response.setHeader() to set a header value, response.addHeader() to add a new header value, response.setIntHeader() to set an header with an integer value and response.setDateHeader() to set a header with a date value (e.g. from System.currentTimeMillis()).
The ColdFusion Markup Language (CFML) uses the tag cfheader to define headers and their values. Status codes can be changed with a statement like and new header lines introduced with a statement like .

Redirect known attack scripts

Another way of defending against fingerprinting utilities is to redirect attack scripts as like httprecon. Within the following .htaccess example the well-known user-agents are detected and redirected to the attackers own computer:
RewriteCond %{HTTP_USER_AGENT} ^Nikto [OR]
RewriteCond %{HTTP_USER_AGENT} ^Mozilla/4.75 [OR]
RewriteCond %{HTTP_USER_AGENT} ^httprecon
RewriteRule ^(.*)$ http://%{REMOTE_HOST}:80 [R=301,L]
This introduces several advantages. First, the attacker is consuming more of his resources which might slow down the scan approach. Second, most of the attack scripts do not recognize the redirect and think the final destination host - which is the attackers own computer - shall be fingerprinted. Thus, in some cases wrong results might be gathered.
However, this blacklist technique only works as long as the attack scripts are detected properly. If the attacker is going to change the approach and behavior of the scanning software, no further redirection might be possible.

Httprecon is a http fingerprinting tool for Windows. The results are based on the analysis of 9 requests (see detailed requests below):
  1. GET existing
  2. GET long request
  3. GET non-existing
  4. GET wrong protocol
  5. HEAD existing
  6. OPTIONS common
  7. DELETE existing
  8. TEST method
  9. Attack Request

Detailed tests

Here is the list of the requests (with default options) sent by the tool:

GET existing

GET / HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Connection: Keep-Alive
Cache-Control: no-cache

GET long request

GET /nnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnnn HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Connection: Keep-Alive
Cache-Control: no-cache

GET non-existing

GET /dX6cZ6.html HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Connection: Keep-Alive
Cache-Control: no-cache

GET wrong protocol

GET / HTTP/9.8
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Connection: Keep-Alive
Cache-Control: no-cache

HEAD existing

HEAD / HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache

OPTIONS common

OPTIONS / HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache

DELETE existing

DELETE / HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache

TEST method

TEST / HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Content-Length: 0
Connection: Keep-Alive
Cache-Control: no-cache

Attack Request

GET /etc/passwd?format=%%&xss="><script>alert('xss');</script>&traversal=../../&sql='%20OR%201; HTTP/1.1
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.11) Gecko/20071127 Firefox/2.0.0.8
Host: 192.168.100.24
Connection: Keep-Alive
Cache-Control: no-cache

Example

Our tests have been run against an Apache 2.2.17 installed on a Debian 5 box. Here is the full signature on the server:
$ /usr/local/apache2/bin/httpd -V
Server version: Apache/2.2.17 (Unix)
Server built: Dec 27 2010 20:54:46
Server's Module Magic Number: 20051115:25
Server loaded: APR 1.4.2, APR-Util 1.3.10
Compiled using: APR 1.4.2, APR-Util 1.3.10
Architecture: 32-bit
Server MPM: Prefork
threaded: no
forked: yes (variable process count)
Server compiled with....
-D APACHE_MPM_DIR="server/mpm/prefork"
-D APR_HAS_SENDFILE
-D APR_HAS_MMAP
-D APR_HAVE_IPV6 (IPv4-mapped addresses enabled)
-D APR_USE_SYSVSEM_SERIALIZE
-D APR_USE_PTHREAD_SERIALIZE
-D SINGLE_LISTEN_UNSERIALIZED_ACCEPT
-D APR_HAS_OTHER_CHILD
-D AP_HAVE_RELIABLE_PIPED_LOGS
-D DYNAMIC_MODULE_LIMIT=128
-D HTTPD_ROOT="/usr/local/apache2"
-D SUEXEC_BIN="/usr/local/apache2/bin/suexec"
-D DEFAULT_PIDLOG="logs/httpd.pid"
-D DEFAULT_SCOREBOARD="logs/apache_runtime_status"
-D DEFAULT_LOCKFILE="logs/accept.lock"
-D DEFAULT_ERRORLOG="logs/error_log"
-D AP_TYPES_CONFIG_FILE="conf/mime.types"
-D SERVER_CONFIG_FILE="conf/httpd.conf"

Trivia and Fun Stuff

During the development of httprecon and the use of the software in professional penetration tests several funny things could be observed:
  • Wordpress is using the header "X-nananana: Batcache" (@ChrisJohnRiley) (09/22/2010)
  • Just one of the major banks in Switzerland is deleting the Server line entirely. (04/25/2009)
  • The host www.ibm.com has a mispelled header line which reads "epKe-Alive" instead of "Keep-Alive". (04/16/2009)
  • A popular swiss travel agency defined the Server line as "Game Cube" which is abviously not true. (11/24/2007)



Sources:

http://www.computec.ch/projekte/httprecon/?s=demo

https://pentestlab.blog/tag/httprecon/

https://www.aldeid.com/wiki/Httprecon

https://www.darknet.org.uk/2008/03/httprecon-advanced-web-server-fingerprinting/

https://github.com/scipag/httprecon-win32

https://latesthackingnews.com/2017/07/09/information-gathering-httprecon-tool/

Quick Sort, Selection Sort and Bubble Sort algorithm in VB6

$
0
0
Here we have an application that measures execution times for the three sorting algorithms: Quick Sort, Selection Sort and Bubble Sort.  A visual interface shows what these algorithms do in real time. The implementation is made in algorithm in Visual Basic 6.0 and the source code is shown below:

Download from me

The quicksortalgorithm was developed in 1959 by Tony Hoare while in the Soviet Union, as a visiting student at Moscow State University. At that time, Hoare worked in a project on machine translation for the National Physical Laboratory. As a part of the translation process, he needed to sort the words of Russian sentences prior to looking them up in a Russian-English dictionary that was already sorted in alphabetic order on magnetic tape. After recognizing that his first idea, insertion sort, would be slow, he quickly came up with a new idea that was Quicksort. He wrote a program in Mercury Autocode for the partition but couldn't write the program to account for the list of unsorted segments. On return to England, he was asked to write code for Shellsort as part of his new job. Hoare mentioned to his boss that he knew of a faster algorithm and his boss bet sixpence that he didn't. His boss ultimately accepted that he had lost the bet. Later, Hoare learned about ALGOL and its ability to do recursion that enabled him to publish the code in Communications of the Association for Computing Machinery, the premier computer science journal of the time.

Quicksort gained widespread adoption, appearing, for example, in Unix as the default library sort subroutine. Hence, it lent its name to the C standard library subroutine qsort and in the reference implementation of Java.

Robert Sedgewick's Ph.D. thesis in 1975 is considered a milestone in the study of Quicksort where he resolved many open problems related to the analysis of various pivot selection schemes including Samplesort, adaptive partitioning by Van Emden as well as derivation of expected number of comparisons and swaps. Bentley and McIlroy incorporated various improvements for use in programming libraries, including a technique to deal with equal elements and a pivot scheme known as pseudomedian of nine, where a sample of nine elements is divided into groups of three and then the median of the three medians from three groups is chosen. Jon Bentley described another simpler and compact partitioning scheme in his book Programming Pearls that he attributed to Nico Lomuto. Later Bentley wrote that he used Hoare's version for years but never really understood it but Lomuto's version was simple enough to prove correct. Bentley described Quicksort as the "most beautiful code I had ever written" in the same essay. Lomuto's partition scheme was also popularized by the textbook Introduction to Algorithms although it is inferior to Hoare's scheme because it does three times more swaps on average and degrades to O(n2) runtime when all elements are equal.

In 2009, Vladimir Yaroslavskiy proposed the new dual pivot Quicksort implementation. In the Java core library mailing lists, he initiated a discussion claiming his new algorithm to be superior to the runtime library’s sorting method, which was at that time based on the widely used and carefully tuned variant of classic Quicksort by Bentley and McIlroy. Yaroslavskiy’s Quicksort has been chosen as the new default sorting algorithm in Oracle’s Java 7 runtime library after extensive empirical performance tests.


Selection sort is a sorting algorithm, specifically an in-place comparison sort. It has O(n2) time complexity, making it inefficient on large lists, and generally performs worse than the similar insertion sort. Selection sort is noted for its simplicity, and it has performance advantages over more complicated algorithms in certain situations, particularly where auxiliary memory is limited.

The algorithm divides the input list into two parts: the sublist of items already sorted, which is built up from left to right at the front (left) of the list, and the sublist of items remaining to be sorted that occupy the rest of the list. Initially, the sorted sublist is empty and the unsorted sublist is the entire input list. The algorithm proceeds by finding the smallest (or largest, depending on sorting order) element in the unsorted sublist, exchanging (swapping) it with the leftmost unsorted element (putting it in sorted order), and moving the sublist boundaries one element to the right.


Bubble sort, sometimes referred to as sinking sort, is a simple sorting algorithm that repeatedly steps through the list to be sorted, compares each pair of adjacent items and swaps them if they are in the wrong order. The pass through the list is repeated until no swaps are needed, which indicates that the list is sorted. The algorithm, which is a comparison sort, is named for the way smaller or larger elements "bubble" to the top of the list. Although the algorithm is simple, it is too slow and impractical for most problems even when compared to insertion sort. It can be practical if the input is usually in sorted order but may occasionally have some out-of-order elements nearly in position.


Implementation:

PublicDeclareSubSleepLib"kernel32.dll"(ByValdwMillisecondsAsLong)

PublicSubQuickSort(vArrayAsVariant,LAsLong,RAsLong)
' Array , LBound() , UBound()
DimiAsLong
DimjAsLong
DimX
DimY

i=L
j=R
X=vArray((L+R)/2)

DoWhile(i<=j)
DoEvents
DoWhile(vArray(i)<XAndi<R)
i=i+1
Loop

DoWhile(X<vArray(j)Andj>L)
j=j-1
Loop

If(i<=j)Then
Y=vArray(i)
vArray(i)=vArray(j)
vArray(j)=Y
i=i+1
j=j-1
EndIf
Loop

If(L<j)ThenQuickSortvArray,L,j
If(i<R)ThenQuickSortvArray,i,R
EndSub

PublicSubQuickSort33(vArrayAsVariant,AccordingToAsInteger,Dimension2SizeAsInteger,LAsInteger,RAsInteger)
' name of array, sorting according to which dimension?, size of second dimension, lbound(), ubound()
DimaAsInteger,iAsInteger,jAsInteger' counters
DimX,Y,z' temporary values

i=L
j=R
X=vArray((L+R)/2,AccordingTo)
DoWhile(i<=j)
DoEvents
DoWhile(vArray(i,AccordingTo)<XAndi<R)
i=i+1
Loop
DoWhile(X<vArray(j,AccordingTo)Andj>L)
j=j-1
Loop
If(i<=j)Then
Y=vArray(i,AccordingTo)
vArray(i,AccordingTo)=vArray(j,AccordingTo)
vArray(j,AccordingTo)=Y
Fora=0ToAccordingTo-1
z=vArray(i,a)
vArray(i,a)=vArray(j,a)
vArray(j,a)=z
Nexta
Fora=AccordingTo+1ToDimension2Size
z=vArray(i,a)
vArray(i,a)=vArray(j,a)
vArray(j,a)=z
Nexta
i=i+1
j=j-1
EndIf
Loop

If(L<j)ThenQuickSort33vArray,AccordingTo,Dimension2Size,L,j
If(i<R)ThenQuickSort33vArray,AccordingTo,Dimension2Size,i,R
EndSub

PublicSubSelectionSort(vArray,LAsInteger,RAsInteger)
' name of array, lbound(), ubound()
DimiAsInteger
DimjAsInteger
Dimbest_value' smallest value in array
Dimbest_jAsInteger
' loop from left to right
Fori=LToR-1
DoEvents
' initialize lowest value
best_value=vArray(i)
best_j=i' initialize lowest value array location
Forj=i+1ToR
' find the lowest value in the array in this loop
IfvArray(j)<best_valueThen
best_value=vArray(j)
best_j=j
EndIf
Nextj
' put the smallest value at the from (left) of the array
' and put the value on the left of the array in the smallest
' value's previous position
vArray(best_j)=vArray(i)
vArray(i)=best_value
Nexti

EndSub

PublicSubQuickSortBars(vArrayAsVariant,LAsInteger,RAsInteger,OptionalSleepTimeAsLong=0)
DimiAsInteger' counter
DimjAsInteger' counter
DimBarVal1' temporary bar value
DimBarVal2' temporary bar value

i=L
j=R
BarVal1=vArray((L+R)/2)

DoWhile(i<=j)
DoEvents
IfSleepTime>0Then
SleepSleepTime
EndIf
DoWhile(vArray(i)<BarVal1Andi<R)
i=i+1
Loop

DoWhile(BarVal1<vArray(j)Andj>L)
j=j-1
Loop

If(i<=j)Then
BarVal2=vArray(i)
vArray(i)=vArray(j)
vArray(j)=BarVal2
frmMain.Bar(i).Value=vArray(i)
frmMain.Bar(j).Value=vArray(j)
i=i+1
j=j-1
EndIf
Loop

If(L<j)ThenQuickSortBarsvArray,L,j,SleepTime
If(i<R)ThenQuickSortBarsvArray,i,R,SleepTime
EndSub

PublicSubSelectionSortBars(vArray,LAsInteger,RAsInteger,OptionalSleepTimeAsLong=0)
' name of array, lbound(), ubound()
DimiAsInteger' counter
DimjAsInteger' counter
Dimbest_value' smallest value in array
Dimbest_jAsInteger

' loop from left to right
Fori=LToR-1
DoEvents
IfSleepTime>0Then
SleepSleepTime
EndIf
' initialize lowest value
best_value=vArray(i)
best_j=i' initialize lowest value array location
Forj=i+1ToR
' find the lowest value in the array in this loop
IfvArray(j)<best_valueThen
best_value=vArray(j)
best_j=j
EndIf
Nextj
' put the smallest value at the from (left) of the array
' and put the value on the left of the array in the smallest
' value's previous position
vArray(best_j)=vArray(i)
vArray(i)=best_value
frmMain.Bar(best_j)=vArray(best_j)
frmMain.Bar(i)=vArray(i)
Nexti
EndSub

Sources:

https://en.wikipedia.org/wiki/Bubble_sort

https://en.wikipedia.org/wiki/Selection_sort

https://en.wikipedia.org/wiki/Quicksort

Range finder with a Laser and a Webcam in Visual Basic 6.0

$
0
0
The author of this ingenious project is a scientist, namely Dr. Todd Danko. I found Dr. Danko to be connected with General Electric, Lockheed Martin and DARPA. Nice to have such people in the VB6 community. Like every VB6 programmer, it's fluent in C ++, Java and ASM. From here I will let his text explain the project. 

Introduction

There are many off the shelf range finding components available including ultrasonic, infrared, and even laser rangefinders. All of these devices work well, but in the field of aerial robotics, weight is a primary concern. It is desirable to get as much functionality out of each component that is added to an air-frame. Miniature robotic rotor craft for example can carry about 100g of payload. It is possible to perform machine vision tasks such as obstacle identification and avoidance though the use of a webcam (or mini wireless camera interfaced to a computer via USB adapter). Better yet, two webcams can provide stereo machine vision thus improving obstacle avoidance because depth can be determined. The drawback of this of course is the addition of the weight of a second camera. This page describes how a mini laser pointer can be configured along with a single camera to provide mono-machine vision with range information.





Theory of Operation

The diagram below shows how projecting a laser dot onto a target that is in the field of view of a camera, the distance to that target may be calculated. The math is very simple, so this technique works very well for machine vision applications that need to run quickly.


So, here is how it works. A laser-beam is projected onto an object in the field of view of a camera. This laser beam is ideally parallel to the optical axis of the camera. The dot from the laser is captured along with the rest of the scene by the camera. A simple algorithm is run over the image looking for the brightest pixels. Assuming that the laser is the brightest area of the scene (which seems to be true for my dollar store laser pointer indoors), the dots position in the image frame is known. Then we need to calculate the range to the object based on where along the y axis of the image this laser dot falls. The closer to the center of the image, the farther away the object is.

As we can see from the diagram earlier in this section, distance (D) may be calculated:

Of course, to solve this equation, you need to know h, which is a constant fixed as the distance between your laser pointer and camera, and theta. Theta is calculated:


Put the two above equations together, we get:

OK, so the number of pixels from the center of the focal plane that the laser dot appears can just be counted from the image. What about the other parameters in this equation? We need to perform a calibration to derive these.

To calibrate the system, we will collect a series of measurements where I know the range to the target, as well as the number of pixels the dot is from the center of the image each time. This data is below:

Calibration Data
pixels from centeractual D (cm)
10329
8145
6558
5571
4990
45109
41127
39159
37189
35218

Using the following equation, we can calculate the actual angle based on the value of h as well as actual distance for each data point.


Now that we have a Theta_actual for each value, we can come up with a relationship that lets us calculate theta from the number of pixels from image center. I used a linear relationship (thus a gain and offset are needed). This seems to work well even though it does not account for the fact that the focal plane is a plane rather than curved at a constant radius around the center of the lens.

From my calibration data, I calculated:

Offset (ro) = -0.056514344 radians

Gain (rpc) = 0.0024259348 radians/pixel

Using:

I solved for calculated distances, as well as error from actual distance from the calibration data:

Actual and Calculated Range Data
pixels from centercalc D (cm)actual D (cm)% error
10329.84292.88
8141.4645-7.87
6557.5558-0.78
5575.81716.77
4993.57903.96
45110.851091.70
41135.941277.04
39153.27159-3.60
37175.66189-7.06
35205.70218-5.64


Components

There are not a lot of parts in my sample range finder. I used a piece of cardboard to hold a laser pointer to a webcam so that the laser pointer points in a direction that is parallel to that of the camera. The parts seen below are laid out on a one inch grid for reference.



My assembled range finder looks like this:


Software

I have written software two ways, one using visual c++ and the other using visual basic. You will probably find that the visual basic version of the software is much easier to follow than the vc++ code, but with everything, there is a tradeoff. The vc++ code can be put together for free (assuming that you have visual studio), while the vb code requires the purchase of a third party software package (also in addition to visual studio).

Visual Basic

The visual basic code that I have written is available as a package named vb_laser_ranger.zip at the bottom of this page. For this code to work, you will need the VideoOCX ActiveX component installed on your computer. The code that describes the functions found in the main form is seen below:

PrivateSub exit_Click()
' only if running...
If (Timer1.Enabled) Then

Timer1.Enabled = False'Stop Timer
VideoOCX.Stop
VideoOCX.Close

EndIf

End
EndSub

PrivateSub Start_Click() 'Init VideoOCX Control, allocate memory and start grabbing

If (Not Timer1.Enabled) Then
Start.Caption = "Stop"

' Disable internal error messages in VideoOCX
VideoOCX.SetErrorMessages False

' Init control
If (Not VideoOCX.Init) Then
' Init failed. Display error message and end sub
MsgBox VideoOCX.GetLastErrorString, vbOKOnly, "VideoOCX Error"
End
Else
' Allocate memory for global image handle
capture_image = VideoOCX.GetColorImageHandle
' result_image = VideoOCX_Processed.GetColorImageHandle

Timer1.Enabled = True'Start capture timer

' Start Capture mode
If (Not VideoOCX.Start) Then
' Start failed. Display error message and end sub
MsgBox VideoOCX.GetLastErrorString, vbOKOnly, "VideoOCX Error"
End
EndIf
EndIf
Else
Start.Caption = "Start"
Timer1.Enabled = False'Stop Timer
VideoOCX.Stop
VideoOCX.Close
EndIf

EndSub

PrivateSub Timer1_Timer()
' Timer for capturing - handles videoOCXTools
Dim matrix AsVariant
Dim height, width AsInteger
Dim r, c AsInteger
Dim max_r, max_c AsInteger
Dim max_red AsInteger
Dim gain, offset AsVariant
Dim h_cm AsVariant
Dim range AsInteger
Dim pixels_from_center AsInteger

' Calibrated parameter for pixel to distance conversion
gain = 0.0024259348
offset = -0.056514344
h_cm = 5.842

max_red = 0

' Capture an image
If (VideoOCX.Capture(capture_image)) Then

' VideoOCX.Show capture_image

' Matrix transformation initialization
matrix = VideoOCX.GetMatrix(capture_image)

height = VideoOCX.GetHeight
width = VideoOCX.GetWidth

' Image processing code

' The laser dot should not be seen above the middle row (with a little pad)
For r = height / 2 - 20 To height - 1

' Our physical setup is roughly calibrated to make the laser
' dot in the middle columns...dont bother lookng too far away
For c = width / 2 - 25 To width / 2 + 24

' Look for the largest red pixel value in the scene (red laser)
If (matrix(c, r, 2) > max_red) Then
max_red = matrix(c, r, 2)
max_r = r
max_c = c
EndIf
Next c
Next r

' Calculate the distance for the laser dot from middle of frame
pixels_from_center = max_r - 120

' Calculate range in cm based on calibrated parameters
range = h_cm / Tan(pixels_from_center * gain + offset)

' Print laser dot position row and column to screen
row_val.Caption = max_r
col_val.Caption = max_c

' Print range to laser illuminated object to screen
range_val.Caption = range

' Draw a red vertical line to intersect target
For r = 0 To height - 1
matrix(max_c, r, 2) = 255
Next r

' Draw a red horizontal line to intersect target
For c = 0 To width - 1
matrix(c, max_r, 2) = 255
Next c

VideoOCX.ReleaseMatrixToImageHandle (capture_image)

EndIf

VideoOCX.Show capture_image

EndSub


Screen shots from this code can be seen below:




Visual C++

void CTripodDlg::doMyImageProcessing(LPBITMAPINFOHEADER lpThisBitmapInfoHeader)
{
// doMyImageProcessing: This is where you'd write your own image processing code
// Task: Read a pixel's grayscale value and process accordingly

unsignedint W, H; // Width and Height of current frame [pixels]
unsignedint row, col; // Pixel's row and col positions
unsignedlong i; // Dummy variable for row-column vector
unsignedint max_row; // Row of the brightest pixel
unsignedint max_col; // Column of the brightest pixel
BYTE max_val = 0; // Value of the brightest pixel

// Values used for calculating range from captured image data
// these values are only for a specific camera and laser setup
constdouble gain = 0.0024259348; // Gain Constant used for converting
// pixel offset to angle in radians
constdouble offset = -0.056514344; // Offset Constant
constdouble h_cm = 5.842; // Distance between center of camera and laser
double range; // Calculated range
unsignedint pixels_from_center; // Brightest pixel location from center
// not bottom of frame

char str[80]; // To print message
CDC *pDC; // Device context need to print message

W = lpThisBitmapInfoHeader->biWidth; // biWidth: number of columns
H = lpThisBitmapInfoHeader->biHeight; // biHeight: number of rows

for (row = 0; row < H; row++) {
for (col = 0; col < W; col++) {

// Recall each pixel is composed of 3 bytes
i = (unsignedlong)(row*3*W + 3*col);

// If the current pixel value is greater than any other,
// it is the new max pixel
if (*(m_destinationBmp + i) >= max_val)
{
max_val = *(m_destinationBmp + i);
max_row = row;
max_col = col;
}
}
}
// After each frame, reset max pixel value to zero
max_val = 0;

for (row = 0; row < H; row++) {
for (col = 0; col < W; col++) {

i = (unsignedlong)(row*3*W + 3*col);

// Draw a white cross-hair over brightest pixel in the output display
if ((row == max_row) || (col == max_col))
*(m_destinationBmp + i) =
*(m_destinationBmp + i + 1) =
*(m_destinationBmp + i + 2) = 255;
}
}

// Calculate distance of brightest pixel from center rather than bottom of frame
pixels_from_center = 120 - max_row;

// Calculate range in cm based on bright pixel location, and setup specific constants
range = h_cm / tan(pixels_from_center * gain + offset);

// To print message at (row, column) = (75, 580)
pDC = GetDC();

// Display frame coordinates as well as calculated range
sprintf(str, "Max Value at x= %u, y= %u, range= %f cm ",max_col, max_row, range);
pDC->TextOut(75, 580, str);
ReleaseDC(pDC);
}


My complete code for this project is available as a package named LaserRange.zip at the bottom of this page.  Note, to run this executable, you will need to have both qcsdk and the qc543 driver installed on your computer.  Sorry, but you are on your own to find both of these. Below are two examples of the webcam based laser range finder in action. Note how it looks like there are two laser dots in the second example. This "stray light" is caused by internal reflections in the camera. The reflected dot loses intensity as it bounces within the camera so it does not interfere with the algorithm that detects the brightest pixel in the image.



Future Work

One specific improvement that can be made to this webcam based laser range finder is to project a horizontal line rather than a dot onto a target. This way, we could calculate the range for each column of the image rather than just one column. Such a setup would be able to be used to locate areas of maximum range as places that a vehicle could steer towards. Likewise, areas of minimum range would be identified as obstacles to be avoided.

Sources:

https://sites.google.com/site/todddanko/home/webcam_laser_ranger








Stepper Motor Appliance with Visual Basic 6.0

$
0
0

In a previous article entitled "Range finder with a Laser and a Webcam in Visual Basic 6.0" we have shown a project for distance estimation by using a laser and a webcam. Here we have another interesting project by Dr. Todd Danko, that uses VB6.

Download from ME

Introduction

The most advanced pieces of scientific equipment are often both very rare and very expensive. This is a poor combination if your research needs dictate the use of such a device.
For example, scanning electron microscopes, depending on quality, cost millions of dollars. This high price prohibits their purchase for occasional research use. This high price also decreases the probability that there is a facility near by that has both, a scanning electron microscope, and has time to let you use it.
One solution to this scenario is to create a product that allows scanning electron microscopes and possibly other equipment to be used remotely. Such a device would utilize the internet to pass commands to the microscope, as well as return data from the microscope back to the user.

Proposed Solution

Build a prototype of an internet controlled appliance that simulates the remote operation of a scanning electron microscope.
This appliance has four main components:
  • Server Software - to interface with the mechanical device, and the internet
  • Client Software - to interface with the user, and the internet
  • Camera -to simulate output data similar to that of a microscope
  • Stepper Motor X-Y table - to allow the user to change the position of the subject under the microscope

Procedure

Parts

Internet Appliance Electro-Mechanical Parts
PartVendorPart #QuantityPrice
Stepper MotorJameco1518612$6.19
Diode (1N4003)Jameco769708$0.04
Gears (Assorted)Jameco1318011$7.99
Power DriverArrowUNC5804B2$4.22
8255 CardBoondog.com8255 Kit1$59.00
Logitech WebCamBest Buy961237-04031$49.99
BreadboardRadio Shack276-1741$13.49
Battery HolderRadio Shack270-3961$1.79
Wrapping WireRadio Shack278-5011$2.99


Electro-Mechanical

This internet appliance calls for several electro-mechanical components:
  • An X-Y table that is moved by two stepper motors.
    • The X-Y table's purpose is to move the subject of the camera up/down, left/right in the camera's field of view.
    • The X-Y table is constructed of a wood frame, with stepper motors gear mounted.
    • Rotational motions of the stepper motors are transferred into linear motion by a system of wires and pulleys.
  • An 8255 card to interface the server PC with the stepper motor control circuits.
    • The 8255 cards purpose is to provide an interface between the server PC and the stepper motor control circuits. More information on the 8255 card's construction and operation may be found at www.boondog.com.
  • Two stepper motor control circuits.
    • The 5804 chips take digital data in from the 8255 card, and convert it into the phasing of the stepper motor coils to rotate the stepper motors in the desired directions by specified amounts.
    • Below is a schematic for one stepper motor control circuit. Please note that this appliance requires two motors, so two of these circuits must be constructed. The first control circuit is connected to ports A.0 and A.1 of the 8255 card. The second control circuit is connected to ports B.0 and B.1 of the 8255 card.


  • A Camera to collect image data.
    • A camera captures pictures of the subject on the X-Y table.
    • The camera is connected to the server PC in this case through a USB cable.
    • The drivers included with the camera were used to capture image data through the USB port of the server PC.
  • Below is a picture of the overall electro-mechanical setup.
    • Note the ribbon cable coming in from the top of the scene. This attaches to the 8255 card.
    • Note the stepper motor control circuits to the left of the photo.
    • A battery pack is used to power the stepper motors.
    • Note the use of wires wrapped around posts on the X-Y table to convert the motor's motion into linear movement. The platform that the subject would be placed on has been removed to expose the X-Y table mechanism.


Software

The software to control this internet appliance is broken into two groups: Software on the server PC and software on the client PC.

Server

  • The purpose of the server is to interface the internet appliance with the internet.

  • The server has several software components:
    • Visual Basic software to communicate with the client through WinSock, and to communicate with the 8255 Card through the 8255.dll.
    • The visual basic software contains the following components and may be downloaded at the bottom of this page as stepper_control.zip:
      • stepper_control_server.frm
      • stepper_control_server.vbp
      • stepper_control_server.vbw
      • stepper_control_server.exe
    • FTP Server software to make image files written by the Visual Basic software available for retrieval by the client software. For this project, the Titan FTP Server was used.
    • ActiveX component to accept data from the camera, and save it to a file on the server PC's hard drive. For this project, WebCam OCX was used.
  • Note, ActiveX components as well as the 8255.dll must be installed on a PC in addition to the Visual Basic Executable in order for the server to properly function.

Client

  • The purpose of the client is to interface the user with the appliance through the internet.


  • The client has several software components:
    • Visual Basic software to communicate with the server through WinSock, and to communicate with the user through a GUI.
    • The visual basic software contains the following components and may be downloaded at the bottom of this page as stepper_control.zip:
      • stepper_control_client.frm
      • stepper_control_client.vbp
      • stepper_control_client.vbw
      • stepper_control_client.exe
    • ActiveX FTP Client component to allow the client to FTP image files from the server PC's FTP server. For this application, Distinct Software's ftpClient OCX was used.
  • Note, ActiveX components must be installed on a PC in addition to the Visual Basic Executable in order for the client to properly function.

Turbo C

To demonstrate the functionality of the circuit before investing time into writing the server and client software, I wrote some simple code in TurboC.
This code:
  • Prompts the user for the address of the 8255 card.
  • Prompts the user for the direction to rotate the motor.
  • Prompts the user for the number of degrees to rotate the motor.
  • Rotates the stepper motor in the desired direction by the desired amount.

You may download source and executable code at the bottom of this page below in turboc.zip:

Theory of Operation

Here is how the system works:
  • Control data is passed between the server and client using WinSock TCP/IP.
  • Image data is passed from the server to the client using FTP. The client has ftp code built into it, but the server PC must be running third party FTP server software.
  • When a command is sent from the client to the server, the server determines what direction to control the X-Y table.
  • The server then sends commands to the 8255 card by way of the 8255.dll file.
  • Once the server has completed commanding the X-Y table to move, the server saves an image of the new scene.
  • This scene is written to a file on the server PC by means of the WebCam OCX ActiveX component.
  • Upon completion of writing the image file, the server sends a message to the client to indicate that the X-Y table has reached the desired position, and that a new image file is available.
  • When the client receives this message, it opens an FTP dialog with the server PC and retrieves the latest image file.
  • The client then displays the latest image file and allows the user through the client to send more control data.

Operating Procedure

These steps must be taken in the following order to successfully run the internet appliance:
  • Start Up Procedure:

    • Connect appliance to the server PC.
    • Confirm network connectivity between server and client PCs.
    • Determine IP address of server PC.
    • Start the FTP server on the server PC.
    • Start the Stepper Control Server software on the server PC.
    • Select the camera driver when the Stepper Control Server requests it.
    • Start the Stepper Control Client software on the client PC.
    • Enter the server PC's IP address when the Stepper Control Client software requests it.
    • Utilize appliance.
  • Shut Down Procedure:

    • Close Stepper Control Client software.
    • Close Stepper Control Server software.
    • Close FTP server software on server PC.

Conclusion

Utilization of internet appliances such as an internet adapted scanning electron microscope have many advantages. When a piece of equipment is networked through the internet, two main things happen:
  • Expensive and rare pieces of equipment may be brought closer to users all over the world. This allows those who can not justify purchasing equipment to use it after an agreement is made with a host organization.
  • Organizations considering purchase of expensive equipment may be able to diffuse the cost of the equipment through renting time on the machine over the internet. The customer base for this use is of course worldwide.

Source:





Visual Basic 6 SP6 Working in Windows 10 64-bit

$
0
0


Visual Basic 6 SP6 Working in Windows 10 64-bit



Again, thank you to the advanced programmers of the VB6 community!

The story of how Microsoft ran itself into the ground: by Lofaday

$
0
0

The first lesson I learned about "dumb decisions" from Microsoft was when they trashed hardware access when upgrading from Windows 98 and ME. No one noticed that the decision instantly put many thousands of small businesses in trouble, mine included, because the hardware layer access in Windows 98 was the cornerstone of many industrial control systems. All of a sudden I found myself in dozens of meetings explaining to clients why non-NT was no longer made!
An entire Industrial rack mount computer industry was wiped out overnight. The millions invested in motherboard I/O (including printed circuit boards we developed), now wasted. The information systems I sold each meant many MS OS sales. MS didn't even seem to notice or care that their industrial usage arm was holed below the waterline. (Now, in industrial control solutions, Linux has taken over .. it could have been MS).
XP is a lot more stable, and indeed most NT based upgrades have been a considerable improvement, but it wouldn't have been rocket science for Microsoft to have added backward compatibility.
In more general terms, Microsoft need to learn "consistency consistency consistency". The ignorance and arrogance of Microsoft is bewildering if not epic. Ever since Gates left, they seem incapable of applying common sense. Someone in Harvard must have done a popular thesis on obsolescence because MS has adopted it as their mantra! They have abandoned VB6, XNA, SilverLight, Skype API, the original MS Office menus, VS Java, Foxpro, Access, .... Each time they do this, people jump out windows with their careers and businesses in tatters. But Microsoft are just psychopathic at times in their ability to ignore the plight of their own customers. At one point in W8, they even tried to get rid of the desktop! It beggars belief that they expected clients to sit at desks with administrative software running on something that looked more like a giant mobile phone than a desktop PC. Success breeds contempt!
A great story: Once there were two microprocessor giants, Intel and Motorola. Motorola had the best and fastest 16-bit chips and were set to dominate. Then they both decided to come out with a 32 bit chip. Motorola's was miles better than the Intel 32-bit device. Miles better! BUT Intel did something Motorola decided wasn't important... Intel maintained backward compatibility with their original 16-bit processes. Motorola BETRAYED their own client base. They just stuck up their middle finger and said "go back to school and re-learn". NOW -- how many people have heard of Motorola processors these days? And that's the same dumb mistake Microsoft make over and over again. "CONSISTENCY CONSISTENCY CONSISTENCY".
The lesson is that when people buy tech, they are making a decision to invest colossal amounts of time in experience in that tech. My customers used to demand Microsoft because they thought the bigger the company, the safer their investment. But now they are just confused. Even banks use opensource.
Once a company has shown a willingness to betray customer investment with gaay abandon, that company is dead. Teach that one in Harvard!
An article by 

Voice coder

$
0
0



Description: Creating music, I've seen a lot of different virtual instruments and effects. One of the most interesting effects is the vocoder, which allows you to modulate his voice and make it look like a voice for example a robot or something like that. Vocoder was originally used to compress the voice data, and then it began to be used in the music industry. Because I had free time, I decided to write something like this for the sake of the experiment and describe in detail the stages of development for VB6.


Download from VBForums
or
Download from Me

So, take a look at the simplest scheme vocoder:


The signal from the microphone (speech) is fed to a bank of band-pass filters, each of which passes only a small part of the frequency band of the speech signal. The greater the number of filters - the better speech intelligibility. At the same time, the carrier signal (e.g. ramp) is also passed through the same filter bank. Filter output speech signal is fed to envelope detectors which control modulators and outputs a filter carrier signal passes to the other input of the modulator. As a result, each band speech signal adjusts the level of the corresponding band carrier (modulates it). Further, output signals from all modulators are mixed and sent to the output. Further, all signal modulators are mixed and sent to the output. In order to improve speech intelligibility also apply additional blocks, such as the detector "sizzling" sound. So, to begin development necessary to determine the source signals, where they will take. It is possible for example to capture data from a file or directly processed in real-time from a microphone or line input. To test very easy to use file, so we will do and so and so. As the carrier will use an external file looped in a circle, to adjust the tone simply add the ability to change the playback speed, which will change the tone. To capture the sound of the file will use Audio Compression Manager (ACM), with it very convenient to make conversion between formats (because the file can be in any format, you would have to write some functions to different formats). It may be that to convert to the desired format will not correct ACM drivers, then play this file will not be available (although you can try to do it in 2 stages). As input files will use the wav - files, because to work with them in the system has special features to facilitate retrieving data from them.



When loading of form we perform initialization of all components. Capture, playing back the audio size FFT, the amount of overlap, overlapping buffers, creating buffers for integer and complex data. Next, I made a box shape with rounded corners, as use a window without frame (draw in the nonclient area had no desire). Now the whole problem is reduced to handling events - AudioPlayback_NewData and AudioCapture_NewData. First event occurs when the playback device needs another portion of the audio data, the second when the buffer capture, in which we simply copy the data into a temporary buffer from where it will take them at processing AudioPlayback_NewData. The main method - Process, in it we just do the conversion. First we check whether we capture from a file or device. To do this, we check the variable mInpFile, which specifies the name of the input file to capture. If capture is made from a file, then we are using object inpConv, which is an instance of clsTrickWavConverter, convert the data into the format you want us to. If the data is finished (the number of bytes read does not match the passed), it means that we are on the edge of the file and continue to have to start over again. Also check the carrier signal and if it is not set then just copy the input data on output and, in this case, we will hear the raw sound. Otherwise, we translate the data into a complex form (count a real part of the signal and the imaginary zero out) and puts the resulting array in an overlapping buffer. Next, start processing the carrier signal. Because carrier signal we can have a very small length (you can use one wave period), in order to optimize I will do the repetition of the signal if required. Let me explain. For example, if we have a carrier signal 10 ms and 100 ms buffer (for example), then you could just call the conversion each time using ACM overwriting the pointer to the array destination, but it is not optimal. For optimization can be converted only once, and then simply duplicate the data to the end of the array, which we did. Only then do not forget to change the position in the source file, otherwise the next phase of the reading will not be the same and will flicks. We will write to another buffer (rawBuffer). This buffer length is based on the pitch shift. For example, if we want to shift the tone for the amount of semitones (halftones), the buffer size must be rawBuffer 2semitones / 12 times more. Then we simply compress / stretch buffer to a value mFFTSize, which will give us the acceleration / deceleration, and as a result increase / decrease tone. After all the manipulations we write data in an overlapping buffer and start processing. To do this, we pass by the number of overlapping data and handle them. Class objects clsTrickOverlappedBuffer return us the correct data. Processing is clear from the code, as We consider in detail the performance of each class. After processing all of overlap we get the output and convert them to integer suitable for playback. As the setting uses a form frmSettings. As the list of devices using a standard listbox, just going through my drawing class. The list of devices will be added in the following order:
  • A default device predetermined format
  • Device 1
  • Device 2
  • ...
  • Device n
  • Capturing from a file


For testing click on the last point message is used LB_GETITEMRECT, which receives the coordinates and size of the item in the list. If this is not done then click the sheet of paper, if there is an empty space at the bottom will be equivalent to clicking on the last point. In the handler settings button in the main form frmTrickVocoder we check capture device and either open the file for conversion or initialize capture. To adjust the volume and mixing using a logarithmic scale, as the sensitivity of the human ear is not linear.

Source: http://www.vbforums.com/showthread.php?788933-VB6-Vocoder





Graphical audio spectrum visualizer: Trick Spectrum from Microphone, MP3 players, Win10, in Visual Basic 6.0

$
0
0

Here we have a superb app made by Krivous Anatoly Anatolevich. Here is his description on VBForums: The sound is analyzed through a standard recording device, i.e. you can select the microphone and view its spectrum, or you can select stereo mixer and view a spectrum of a playback sound.
Captures via my Microphone

This visualizer allows to adjust the number of displayed octaves, transparency of background and amplification.
You can also load a palette from an external PNG file with 32ARGB format. It also supports the following effects: "blur" and "burning". You can view a spectrum of a signal represented in the two modes: arcs (rings) and sectors (pies). If you use the ring view an octave is mapped to radial coordinate and a semitone to angle. The separated harmonics are placed along the same line; color represents an intensity. The sectors view maps the amount of signal to the radial coordinate, the frequency in octaves to the color, the frequency in semitones to the angular coordinate.
This idea was suggested to me by Vladislav Petrovky (aka Hacker). His idea was a little different.

Initially it creates the buffers for sound and buffer bitmaps. Further it starts the sound capture process and waits when a buffer will be filled. When a buffer has been filled it begins processing. Firstly it performs the Fast Fourier Transform in order to transform a signal to the frequency domain form. Before performing it applies the Hamming window in order to reduce distortions because a signal has discontinuity at the edges of a buffer. When a signal has been translated to the frequency domain the buffer contains complex value that represent the vectors. The module (length) of a vector implies the energy of signal in that frequency and the argument (angle) implies phase of a harmonic in that frequency.


Screenshot of the menu
We need the energy of frequency although the phase information allows to determine the frequency more accurately considering the phase difference. I don't use phase information in this project. The drawing method is different for each appearance mode. In order to boost the work it uses the precalculated coordinates named MapData. This array contains the angles of arcs and sectors for the current appearance mode. When coordinates has been calculated it calculates the amount of frequency for each FFT bin figuring out the length of a vector. This value is uses as the index in the color palette after converting the value to a range from 0 to 255. Further GDI+ draws the necessary primitives depending on the appearance mode. Note that all drawing occur onto the buffer bitmap not on window. I specially have not mentioned about the Release procedure that animates the background. This procedure applies an effect to the buffer bitmap before signal processing. It uses the Fade property that determines the speed of the disappearance of previous drawing bitmap. It just decrease the alpha value of the entire bitmap. When you use an effect it also works with the bits of the buffer bitmap and decreases the alpha value. For instance, if the blur effect has been selected it averages the near pixels (analog of low-pass filtering) then it decreases the alpha value for all pixels depending on Fade property. Eventually it draws buffer bitmap onto the main window. Thus it draws the energy of the spectrum of signal in the polar coordinates. It can be used as the start point for the notes or chord recognition.


Download from VBForums

Download from me



Here is a video of the app:










Solution of the differential equation

$
0
0
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Cephes Math Library Release 2.8: June, 2000
'Copyright by Stephen L. Moshier
'
'Contributors:
' * Sergey Bochkanov (ALGLIB project). Translation from C to
' pseudocode.
'
'See subroutines comments for additional copyrights.
'
'>>> SOURCE LICENSE >>>
'This program is free software; you can redistribute it and/or modify
'it under the terms of the GNU General Public License as published by
'the Free Software Foundation (www.fsf.org); either version 2 of the
'License, or (at your option) any later version.
'
'This program is distributed in the hope that it will be useful,
'but WITHOUT ANY WARRANTY; without even the implied warranty of
'MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
'GNU General Public License for more details.
'
'A copy of the GNU General Public License is available at
'http://www.fsf.org/licensing/licenses
'
'>>> END OF LICENSE >>>
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Routines
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Airy function
'
'Solution of the differential equation
'
'y"(x) = xy.
'
'The function returns the two independent solutions Ai, Bi
'and their first derivatives Ai'(x), Bi'(x).
'
'Evaluation is by power series summation for small x,
'by rational minimax approximations for large x.
'
'
'
'ACCURACY:
'Error criterion is absolute when function <= 1, relative
'when function > 1, except * denotes relative error criterion.
'For large negative x, the absolute error increases as x^1.5.
'For large positive x, the relative error increases as x^1.5.
'
'Arithmetic domain function # trials peak rms
'IEEE -10, 0 Ai 10000 1.6e-15 2.7e-16
'IEEE 0, 10 Ai 10000 2.3e-14* 1.8e-15*
'IEEE -10, 0 Ai' 10000 4.6e-15 7.6e-16
'IEEE 0, 10 Ai' 10000 1.8e-14* 1.5e-15*
'IEEE -10, 10 Bi 30000 4.2e-15 5.3e-16
'IEEE -10, 10 Bi' 30000 4.9e-15 7.3e-16
'
'Cephes Math Library Release 2.8: June, 2000
'Copyright 1984, 1987, 1989, 2000 by Stephen L. Moshier
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicSub Airy(ByVal x AsDouble, _
ByRef Ai AsDouble, _
ByRef Aip AsDouble, _
ByRef Bi AsDouble, _
ByRef Bip AsDouble)
Dim z AsDouble
Dim zz AsDouble
Dim t AsDouble
Dim f AsDouble
Dim g AsDouble
Dim uf AsDouble
Dim ug AsDouble
Dim k AsDouble
Dim zeta AsDouble
Dim theta AsDouble
Dim domflg AsLong
Dim c1 AsDouble
Dim c2 AsDouble
Dim sqrt3 AsDouble
Dim sqpii AsDouble
Dim AFN AsDouble
Dim AFD AsDouble
Dim AGN AsDouble
Dim AGD AsDouble
Dim APFN AsDouble
Dim APFD AsDouble
Dim APGN AsDouble
Dim APGD AsDouble
Dim AN AsDouble
Dim AD AsDouble
Dim APN AsDouble
Dim APD AsDouble
Dim BN16 AsDouble
Dim BD16 AsDouble
Dim BPPN AsDouble
Dim BPPD AsDouble

sqpii = 0.564189583547756
c1 = 0.355028053887817
c2 = 0.258819403792807
sqrt3 = 1.73205080756888
domflg = 0#
If x > 25.77 Then
Ai = 0#
Aip = 0#
Bi = MaxRealNumber
Bip = MaxRealNumber
ExitSub
End If
If x < -2.09 Then
domflg = 15#
t = Sqr(-x)
zeta = -(2# * x * t / 3#)
t = Sqr(t)
k = sqpii / t
z = 1# / zeta
zz = z * z
AFN = -0.131696323418332
AFN = AFN * zz - 0.626456544431912
AFN = AFN * zz - 0.693158036036933
AFN = AFN * zz - 0.279779981545119
AFN = AFN * zz - 0.04919001326095
AFN = AFN * zz - 4.06265923594885E-03
AFN = AFN * zz - 1.59276496239262E-04
AFN = AFN * zz - 2.77649108155233E-06
AFN = AFN * zz - 1.67787698489115E-08
AFD = 1#
AFD = AFD * zz + 13.3560420706553
AFD = AFD * zz + 32.6825032795225
AFD = AFD * zz + 26.73670409415
AFD = AFD * zz + 9.1870740290726
AFD = AFD * zz + 1.47529146771666
AFD = AFD * zz + 0.115687173795188
AFD = AFD * zz + 4.40291641615211E-03
AFD = AFD * zz + 7.54720348287414E-05
AFD = AFD * zz + 4.5185009297058E-07
uf = 1# + zz * AFN / AFD
AGN = 1.97339932091686E-02
AGN = AGN * zz + 0.391103029615688
AGN = AGN * zz + 1.06579897599596
AGN = AGN * zz + 0.93916922981665
AGN = AGN * zz + 0.351465656105548
AGN = AGN * zz + 6.33888919628925E-02
AGN = AGN * zz + 5.85804113048388E-03
AGN = AGN * zz + 2.82851600836737E-04
AGN = AGN * zz + 6.98793669997261E-06
AGN = AGN * zz + 8.11789239554389E-08
AGN = AGN * zz + 3.41551784765924E-10
AGD = 1#
AGD = AGD * zz + 9.30892908077442
AGD = AGD * zz + 19.8352928718312
AGD = AGD * zz + 15.5646628932865
AGD = AGD * zz + 5.47686069422975
AGD = AGD * zz + 0.954293611618962
AGD = AGD * zz + 8.64580826352392E-02
AGD = AGD * zz + 4.12656523824223E-03
AGD = AGD * zz + 1.01259085116509E-04
AGD = AGD * zz + 1.17166733214414E-06
AGD = AGD * zz + 4.9183457006293E-09
ug = z * AGN / AGD
theta = zeta + 0.25 * PI()
f = Sin(theta)
g = Cos(theta)
Ai = k * (f * uf - g * ug)
Bi = k * (g * uf + f * ug)
APFN = 0.185365624022536
APFN = APFN * zz + 0.886712188052584
APFN = APFN * zz + 0.987391981747399
APFN = APFN * zz + 0.401241082318004
APFN = APFN * zz + 7.10304926289631E-02
APFN = APFN * zz + 5.90618657995662E-03
APFN = APFN * zz + 2.33051409401777E-04
APFN = APFN * zz + 4.08718778289035E-06
APFN = APFN * zz + 2.48379932900442E-08
APFD = 1#
APFD = APFD * zz + 14.7345854687503
APFD = APFD * zz + 37.542393343549
APFD = APFD * zz + 31.4657751203046
APFD = APFD * zz + 10.9969125207299
APFD = APFD * zz + 1.78885054766999
APFD = APFD * zz + 0.141733275753663
APFD = APFD * zz + 5.44066067017226E-03
APFD = APFD * zz + 9.39421290654511E-05
APFD = APFD * zz + 5.65978713036027E-07
uf = 1# + zz * APFN / APFD
APGN = -3.55615429033082E-02
APGN = APGN * zz - 0.637311518129436
APGN = APGN * zz - 1.70856738884312
APGN = APGN * zz - 1.50221872117317
APGN = APGN * zz - 0.563606665822103
APGN = APGN * zz - 0.102101031120217
APGN = APGN * zz - 9.48396695961445E-03
APGN = APGN * zz - 4.60325307486781E-04
APGN = APGN * zz - 1.14300836484517E-05
APGN = APGN * zz - 1.33415518685547E-07
APGN = APGN * zz - 5.63803833958894E-10
APGD = 1#
APGD = APGD * zz + 9.8586580169613
APGD = APGD * zz + 21.6401867356586
APGD = APGD * zz + 17.3130776389749
APGD = APGD * zz + 6.17872175280829
APGD = APGD * zz + 1.08848694396321
APGD = APGD * zz + 9.95005543440888E-02
APGD = APGD * zz + 4.78468199683887E-03
APGD = APGD * zz + 1.18159633322839E-04
APGD = APGD * zz + 1.37480673554219E-06
APGD = APGD * zz + 5.79912514929148E-09
ug = z * APGN / APGD
k = sqpii * t
Aip = -(k * (g * uf + f * ug))
Bip = k * (f * uf - g * ug)
ExitSub
End If
If x >= 2.09 Then
domflg = 5#
t = Sqr(x)
zeta = 2# * x * t / 3#
g = Exp(zeta)
t = Sqr(t)
k = 2# * t * g
z = 1# / zeta
AN = 0.346538101525629
AN = AN * z + 12.0075952739646
AN = AN * z + 76.2796053615235
AN = AN * z + 168.089224934631
AN = AN * z + 159.756391350164
AN = AN * z + 70.5360906840444
AN = AN * z + 14.026469116339
AN = AN * z + 1#
AD = 0.56759453263877
AD = AD * z + 14.7562562584847
AD = AD * z + 84.5138970141475
AD = AD * z + 177.3180881454
AD = AD * z + 164.23469287153
AD = AD * z + 71.4778400825576
AD = AD * z + 14.0959135607834
AD = AD * z + 1#
f = AN / AD
Ai = sqpii * f / k
k = -(0.5 * sqpii * t / g)
APN = 0.613759184814036
APN = APN * z + 14.7454670787755
APN = APN * z + 82.0584123476061
APN = APN * z + 171.184781360976
APN = APN * z + 159.317847137142
APN = APN * z + 69.9778599330103
APN = APN * z + 13.9470856980482
APN = APN * z + 1#
APD = 0.334203677749737
APD = APD * z + 11.1810297306158
APD = APD * z + 71.172735214786
APD = APD * z + 158.778084372838
APD = APD * z + 153.206427475809
APD = APD * z + 68.675230459278
APD = APD * z + 13.8498634758259
APD = APD * z + 1#
f = APN / APD
Aip = f * k
If x > 8.3203353 Then
BN16 = -0.253240795869364
BN16 = BN16 * z + 0.575285167332467
BN16 = BN16 * z - 0.329907036873225
BN16 = BN16 * z + 0.06444040689482
BN16 = BN16 * z - 3.82519546641337E-03
BD16 = 1#
BD16 = BD16 * z - 7.15685095054035
BD16 = BD16 * z + 10.6039580715665
BD16 = BD16 * z - 5.23246636471251
BD16 = BD16 * z + 0.957395864378384
BD16 = BD16 * z - 0.055082814716355
f = z * BN16 / BD16
k = sqpii * g
Bi = k * (1# + f) / t
BPPN = 0.465461162774652
BPPN = BPPN * z - 1.08992173800494
BPPN = BPPN * z + 0.638800117371828
BPPN = BPPN * z - 0.126844349553103
BPPN = BPPN * z + 7.6248784434211E-03
BPPD = 1#
BPPD = BPPD * z - 8.70622787633159
BPPD = BPPD * z + 13.8993162704553
BPPD = BPPD * z - 7.14116144616431
BPPD = BPPD * z + 1.34008595960681
BPPD = BPPD * z - 7.84273211323342E-02
f = z * BPPN / BPPD
Bip = k * t * (1# + f)
ExitSub
End If
EndIf
f = 1#
g = x
t = 1#
uf = 1#
ug = x
k = 1#
z = x * x * x
DoWhile t > MachineEpsilon
uf = uf * z
k = k + 1#
uf = uf / k
ug = ug * z
k = k + 1#
ug = ug / k
uf = uf / k
f = f + uf
k = k + 1#
ug = ug / k
g = g + ug
t = Abs(uf / f)
Loop
uf = c1 * f
ug = c2 * g
If domflg Mod 2# = 0# Then
Ai = uf - ug
EndIf
If domflg \ 2# Mod 2# = 0# Then
Bi = sqrt3 * (uf + ug)
EndIf
k = 4#
uf = x * x / 2#
ug = z / 3#
f = uf
g = 1# + ug
uf = uf / 3#
t = 1#
DoWhile t > MachineEpsilon
uf = uf * z
ug = ug / k
k = k + 1#
ug = ug * z
uf = uf / k
f = f + uf
k = k + 1#
ug = ug / k
uf = uf / k
g = g + ug
k = k + 1#
t = Abs(ug / g)
Loop
uf = c1 * f
ug = c2 * g
If domflg \ 4# Mod 2# = 0# Then
Aip = uf - ug
EndIf
If domflg \ 8# Mod 2# = 0# Then
Bip = sqrt3 * (uf + ug)
EndIf
EndSub

Fast kernel

$
0
0
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Copyright (c) 2009, Sergey Bochkanov (ALGLIB project).
'
'>>> SOURCE LICENSE >>>
'This program is free software; you can redistribute it and/or modify
'it under the terms of the GNU General Public License as published by
'the Free Software Foundation (www.fsf.org); either version 2 of the
'License, or (at your option) any later version.
'
'This program is distributed in the hope that it will be useful,
'but WITHOUT ANY WARRANTY; without even the implied warranty of
'MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
'GNU General Public License for more details.
'
'A copy of the GNU General Public License is available at
'http://www.fsf.org/licensing/licenses
'
'>>> END OF LICENSE >>>
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Routines
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixRank1F(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() As Complex, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByRef U() As Complex, _
ByVal IU AsLong, _
ByRef V() As Complex, _
ByVal IV AsLong) AsBoolean
Dim Result AsBoolean

Result = False

CMatrixRank1F = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixRank1F(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() AsDouble, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByRef U() AsDouble, _
ByVal IU AsLong, _
ByRef V() AsDouble, _
ByVal IV AsLong) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixRank1F = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixMVF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() As Complex, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpA AsLong, _
ByRef X() As Complex, _
ByVal IX AsLong, _
ByRef Y() As Complex, _
ByVal IY AsLong) AsBoolean
Dim Result AsBoolean

Result = False

CMatrixMVF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixMVF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() AsDouble, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpA AsLong, _
ByRef X() AsDouble, _
ByVal IX AsLong, _
ByRef Y() AsDouble, _
ByVal IY AsLong) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixMVF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixRightTRSMF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() As Complex, _
ByVal I1 AsLong, _
ByVal J1 AsLong, _
ByVal IsUpper AsBoolean, _
ByVal IsUnit AsBoolean, _
ByVal OpType AsLong, _
ByRef X() As Complex, _
ByVal I2 AsLong, _
ByVal J2 AsLong) AsBoolean
Dim Result AsBoolean

Result = False

CMatrixRightTRSMF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixLeftTRSMF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() As Complex, _
ByVal I1 AsLong, _
ByVal J1 AsLong, _
ByVal IsUpper AsBoolean, _
ByVal IsUnit AsBoolean, _
ByVal OpType AsLong, _
ByRef X() As Complex, _
ByVal I2 AsLong, _
ByVal J2 AsLong) AsBoolean
Dim Result AsBoolean

Result = False

CMatrixLeftTRSMF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixRightTRSMF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() AsDouble, _
ByVal I1 AsLong, _
ByVal J1 AsLong, _
ByVal IsUpper AsBoolean, _
ByVal IsUnit AsBoolean, _
ByVal OpType AsLong, _
ByRef X() AsDouble, _
ByVal I2 AsLong, _
ByVal J2 AsLong) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixRightTRSMF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixLeftTRSMF(ByVal M AsLong, _
ByVal N AsLong, _
ByRef A() AsDouble, _
ByVal I1 AsLong, _
ByVal J1 AsLong, _
ByVal IsUpper AsBoolean, _
ByVal IsUnit AsBoolean, _
ByVal OpType AsLong, _
ByRef X() AsDouble, _
ByVal I2 AsLong, _
ByVal J2 AsLong) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixLeftTRSMF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixSYRKF(ByVal N AsLong, _
ByVal K AsLong, _
ByVal Alpha AsDouble, _
ByRef A() As Complex, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpTypeA AsLong, _
ByVal Beta AsDouble, _
ByRef C() As Complex, _
ByVal IC AsLong, _
ByVal JC AsLong, _
ByVal IsUpper AsBoolean) AsBoolean
Dim Result AsBoolean

Result = False

CMatrixSYRKF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixSYRKF(ByVal N AsLong, _
ByVal K AsLong, _
ByVal Alpha AsDouble, _
ByRef A() AsDouble, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpTypeA AsLong, _
ByVal Beta AsDouble, _
ByRef C() AsDouble, _
ByVal IC AsLong, _
ByVal JC AsLong, _
ByVal IsUpper AsBoolean) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixSYRKF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction RMatrixGEMMF(ByVal M AsLong, _
ByVal N AsLong, _
ByVal K AsLong, _
ByVal Alpha AsDouble, _
ByRef A() AsDouble, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpTypeA AsLong, _
ByRef B() AsDouble, _
ByVal IB AsLong, _
ByVal JB AsLong, _
ByVal OpTypeB AsLong, _
ByVal Beta AsDouble, _
ByRef C() AsDouble, _
ByVal IC AsLong, _
ByVal JC AsLong) AsBoolean
Dim Result AsBoolean

Result = False

RMatrixGEMMF = Result
EndFunction


''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'Fast kernel
'
' -- ALGLIB routine --
' 19.01.2010
' Bochkanov Sergey
'
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
PublicFunction CMatrixGEMMF(ByVal M AsLong, _
ByVal N AsLong, _
ByVal K AsLong, _
ByRef Alpha_ As Complex, _
ByRef A() As Complex, _
ByVal IA AsLong, _
ByVal JA AsLong, _
ByVal OpTypeA AsLong, _
ByRef B() As Complex, _
ByVal IB AsLong, _
ByVal JB AsLong, _
ByVal OpTypeB AsLong, _
ByRef Beta_ As Complex, _
ByRef C() As Complex, _
ByVal IC AsLong, _
ByVal JC AsLong) AsBoolean
Dim Result AsBoolean
Dim Alpha As Complex
Dim Beta As Complex
Alpha = Alpha_
Beta = Beta_

Result = False

CMatrixGEMMF = Result
EndFunction

Discrete Probability Detector algorithm

$
0
0
'###################################################################################################
'# John Wiley & Sons, Inc.                                                                         #
'# #
'# Book: Markov Chains: From Theory To Implementation And Experimentation #
'# Author: Dr. Paul Gagniuc #
'# Data: 01/05/2017 #
'# #
'# Title: #
'# Discrete Probability Detector #
'# #
'# Short Description: #
'# The purpose of this algorithm is to convert any string into a probability matrix. #
'#_______________________ #
'# Detailed description: \ #
'# This algorithm is an advanced variation of the "ExtractProb" function from the book. The #
'# main difference between "ExtractProb" function and the DPD algorithm is the automatic #
'# identification of states. #
'#_________________________________________________________________________________________________#
'# Initially, the states are identified in the first phase. Each new letter found in "S" is #
'# appended to the string forming in variable "a". Thus, variable "a" gradually increases until #
'# all types of letters from "S" are identified. #
'#_________________________________________________________________________________________________#
'# In the second phase the elements of matrix "m" are filled with zero values for later #
'# purposes. Also, in the second phase the first column of matrix "e" is filled with letters #
'# found in variable "a", and the second column of matrix "e" is filled with zero values for #
'# later use. #
'#_________________________________________________________________________________________________#
'# In the third phase, the transitions between letters of "S" are counted and stored in #
'# matrix "m". #
'# The strategy in this particular case is to fill matrix "m" with transition counts before the #
'# last letter in "S" is reached. In this case, the first column of matrix "e" already contains #
'# the letters from variable "a". The two components of vector "l" contain the "i" and "i+1" #
'# letters from "S". The count of individual transitions between letters is made by a comparison #
'# between vector "l" and the elements from the first column of matrix "e". The number of rows #
'# in matrix "m" and matrix "e" is the same, namely "d". Therefore, an extra loop can be avoided #
'# by mapping matrix "m" through a coordinate system. For instance, if the letter from position #
'# "i" in "S" stored in "l(0)" and the letter from "j" row in matrix "e" (e(j,0)) are the same #
'# then variable "r = j". Likewise, if the letter "i+1" stored in l(1) and the letter from e(j,0) #
'# are the same then variable "c = j". Variable "r" represents the rows of matrix "m", whereas #
'# variable "c" represents the columns of matrix "m" (m(r, c)). #
'# Thus, at each step through "S", an element of matrix "m" is always incremented according to #
'# the coordinates received from "r" and "c". This "coordinate" approach greatly increases the #
'# processing speed of the algorithm. The number of loops = (k-1)*d, where "d" represents the #
'# number of states (or letter types), and "k" is the number of letters in "S". When the letter #
'# stored in "l(0)" and the letter from "j" row in matrix "e" are the same, the second column of #
'# matrix "e" is also incremented. The second column of matrix "e" stores the number of #
'# appearances for each type of letter in "S". #
'#_________________________________________________________________________________________________#
'# In the fourth phase, the counts from matrix "m" elements are divided by the counts from the #
'# second column of matrix "e". The result of this division is stored in the same position in #
'# matrix "m", and represents a transition probability. #
'#_________________________________________________________________________________________________#
'# #
'# Special considerations: #
'# #
'# If a state at the end of "S" (ie HAHAAAHQ) does not occur in the rest of "S" then matrix "m" #
'# will contain a row with all elements on zero. Since it is at the end of "S", the letter does #
'# not make a transition to anything. If a state from the beginning of "S" (ie. QHAHAAAH) does #
'# not occur in the rest of "S" then matrix "m" will contain a column with all elements on zero. #
'# Since the first letter it is only seen at the beginning of "S", no other letter makes a #
'# transition to it. #
'# #
'# The meaning of variables: #
'# _____________________________________________________________________________________ #
'# S = |The string that is being analyzed. _| #
'# _____________________________________________________________________________________ #
'# q = |It is a flag variable with initial value of 1. The value of q becomes zero only if a | #
'# |letter x in the "S" string coresponds with a letter y in the "a" string. _| #
'# _____________________________________________________________________________________ #
'# a = |The variable that holds the letters representing the states. The variable gradually | #
'# |increases in length as the "S" string is analyzed. At each loop, a new letter is | #
'# |added to variable "a" only if the value of q becomes zero. Thus, at the end of the | #
'# |first loop the number of letters in the variable is equal to the total number | #
'# |of states. _| #
'# _____________________________________________________________________________________ #
'# d = |Represents the total number of states and is the length of "a" variable. _| #
'# _____________________________________________________________________________________ #
'# m = |The main probability matrix which the function produces. _| #
'# _____________________________________________________________________________________ #
'# k = |Represents the length of the "S" string. _| #
'# _____________________________________________________________________________________ #
'# e = |It is a matrix with two columns, namely column 0 and 1. Column 0 stores all the | #
'# |letters found in "a". Column 1 stores the number of appearances for each type | #
'# |of letter in "S". _| #
'# _____________________________________________________________________________________ #
'# l = |Is a vector with two components. Vector "l" contains the "i" and "i+1" letters | #
'# |from "S". _| #
'# #
'###################################################################################################

PrivateSub MakeMatrix_Click()
Discrete_Probability_Detector (InP.Text)
EndSub

Function Discrete_Probability_Detector(ByVal S AsString)

Dim e() AsString
Dim m() AsString
Dim l(0 To 1) AsString

k = Len(S)
w = 1

For i = 1 To k
q = 1
For j = 0 To Len(a)
x = Mid(S, i, 1)
y = Mid(a, j + 1, 1)
If x = y Then q = 0
Next j
If q = 1 Then a = a & x
Next i

d = Len(a)

ReDim e(w To d, 0 To 1) AsString
ReDim m(w To d, w To d) AsString

For i = w To d
For j = w To d
m(i, j) = 0
If j = w Then
e(i, 0) = Mid(a, i, 1)
e(i, 1) = 0
EndIf
Next j
Next i

For i = 1 To k - 1
l(0) = Mid(S, i, 1)
l(1) = Mid(S, i + 1, 1)
For j = w To d
If l(0) = e(j, 0) Then
e(j, 1) = Val(e(j, 1)) + 1
r = j
EndIf
If l(1) = e(j, 0) Then c = j
Next j
m(r, c) = Val(m(r, c)) + 1
Next i

tmp = "S="& S & vbCrLf & vbCrLf
tmp = tmp & "The algorithm detected a total of "& (d - w + 1) & " states."& vbCrLf & vbCrLf
tmp = tmp & MatrixPaint(w, d, m, a, "(C)", "Count:") & vbCrLf

For i = w To d
For j = w To d
If Val(e(i, 1)) > 0 Then
m(i, j) = Val(m(i, j)) / Val(e(i, 1))
EndIf
Next j
Next i

tmp = tmp & MatrixPaint(w, d, m, a, "(P)", "Transition matrix M:")

OutPut.Text = tmp

EndFunction


Function MatrixPaint(w, d, ByVal m AsVariant, a, n, ByVal msg AsString) AsString

Dim e() AsString
ReDim e(1 To d) AsString

d = Len(a)
q = "| "
h = "|_____|"
l = vbCrLf

For i = (w - 1) To d
If i = (w - 1) Then t = t & l & "."
t = t & "_____."
If i = d Then t = t & l & "| "& n & " | "
Next i

For i = w To d
e(i) = Mid(a, i, 1)
t = t & e(i) & " | "
h = h & "_____|"
Next i

t = t & l & h & l

For i = w To d
For j = w To d
v = Round(m(i, j), 2)
u = Mid(q, 1, Len(q) - Len(v))
If j = d Then o = "|"Else o = ""
For b = w To d
If j = w And i = b Then
t = t & "| "& e(i) & ""
EndIf
Next b
t = t & u & v & o
Next j
t = t & l & h & l
Next i

MatrixPaint = msg & " M["& Val(d - w + 1) & ","& Val(d - w + 1) & "]"& l & t & l

EndFunction


PrivateSub Form_Resize()
If DPD.ScaleWidth > 0 Then
OutPut.Width = DPD.ScaleWidth - OutPut.Left - 10
OutPut.Height = DPD.ScaleHeight - OutPut.Top - 10
EndIf
EndSub

Source: Gagniuc, Paul A. (2017). Markov Chains: From Theory to Implementation and Experimentation. USA, NJ: John Wiley & Sons. pp. 1–235. ISBN 978-1-119-38755-8.

Experimenting with Markov Chains: Prediction and Simulation

$
0
0


For those interested in experimenting with Markov Chains, we found a new type of app implemented in four or five different programming languages, including VB6. The applications below represent a prediction and a simulator for different experiments related to Markov Chains, both developed by Dr. Paul A. Gagniuc for a math book (Gagniuc, Paul A. (2017). Markov Chains: From Theory to Implementation and Experimentation. USA, NJ: John Wiley & Sons. pp. 1–235. ISBN 978-1-119-38755-8.). These apps are available as binary files and source code.


The prediction app:


Markov Chains - Prediction Framework

The simulation app:

Markov Chains - Simulation Framework

A weather prediction application with animation:


Download from me
Download from Wiley

Markov Chains - The Weather


Sources:

1. https://www.statisticsviews.com/details/feature/10822963/Markov-Chains-From-Theory-to-Implementation-and-Experimentation-An-interview-wit.html

2. https://www.wiley.com/en-gb/Markov+Chains%3A+From+Theory+to+Implementation+and+Experimentation-p-9781119387558

3. https://transition-matrix.blogspot.com/




Windows Information Provider (VB6 open source project)

$
0
0
Windows Information Provider Version 1.2.2 is an advanced app made by A_X_O (unfortunately I did not find his real name). It is a software that can teach you about everything inside the Windows 10 OS. This project is open source and can be modified, you can take parts of it as you need and you can ask A_X_O a little bit more about it (if he has the time to do so). You may wish to search for A_X_O on PSC/Internet, as he has published many advanced software as open source, made in the great VB6 programming language!

Download VB6 source code from PSC

Download VB6 from MediaFire

Download from ME

Final update: September 05th 2019
Now In Complete Applications Section

Drives: Drive, Label, File System, Serial...
Object Search: Object Name, DOS Path, Extension...
System: Description, Bootup State, Manufacturer...
Services: Service Name, ProcessID, State...
Accounts: Domain, Account, Password Required...
Software: Program Groups, Reliability Records, Installed Software...
Registry Search: Search Keys, Value, Data
Processes: Command Line, Handle, Parent Process ID, ProcessID...
TCP/UDP Tables: TCP/IP V4 & V6 Raw Data, UDP/IP V4 & V6 Raw Data
Peripherals: Keyboard, Pointing Device, Sound Card...
Recycle Bin Info: Item Count, Size
Processor: Current Clock Speed, Manufacturer...
Memory Info: BankLabel, Capacity, Manufacturer...
Security Settings: Anti-Malware, Anti-Spyware, Anti-Virus...
WMI Folder Listings: Details of Directories from WMI
WMI File Listings: Details of Files from WMI
View Hidden Object Status: View and Set Hidden Object Status
Common Folders: Quick Access to Common Directories
Google Chrome Extensions:Profile, Extension ID, Name, Version, Permissions, Installed, Key

Windows Information Provider Version 1.2.2













Greatest common divisor (by Davide Chiappetta)

$
0
0
GCD (Greatest Common Divisor) of two numbers is the largest number that divides both of them. For example GCD of 20 and 28 is 4 and GCD of 98 and 56 is 14. In mathematics, the greatest common divisor (gcd) of two or more integers, which are not all zero, is the largest positive integer that divides each of the integers. For example, the gcd of 8 and 12 is 4.

Source:
https://davidechiappetta.wordpress.com/
http://davidechiappetta.blogspot.com/

What Year Is It? VB6 Payload Crypter ! The year is 2020 !

$
0
0
What Year Is It? VB6 Payload Crypter
 JUNE 07, 2018
Last year, researchers identified new crimeware, Loki-Bot, which steals data and login credentials. Loki-Bot is generally distributed through malicious spam, and is difficult to identify without getting into the malware. Loki-Bot crimeware targets Windows, in contrast to the recent Android banking ransomware, Loki Bot. While the crimeware is not as prevalent in the wild, it has some unique and differentiating characteristics.


Loki-Bot’s crypter is especially interesting and unique because it utilizes Visual Basic 6.0 to load multiple stages of shellcode to deliver the Loki-Bot payload. We saw an interesting sample highlighted by @DissectMalware on Twitter and decided to take a closer look for ourselves. We’ll walk through Loki-Bot’s crypter functionality, the first and second stage shellcodes, the payload, and then provide some thoughts on stopping these kinds of attacks and what we can expect to see next.


Loki-Bot Crypter Functionality
The main Visual Basic compiled binary uses a raw pointer access technique to jump into the first stage shellcode which then calls the second-stage shellcode that is executed off of the stack. The first stage shellcode disables data execution prevention (DEP) to make the stack executable, and uses jmp esp to jump into the stage 2 shellcode to allow it to begin execution. Stage 2 then sets up persistence, decrypts the payload, and executes the payload contents by using process hollowing. In this case the payload is Loki-Bot, crimeware designed to steal private information from a system.  Loki-Bot’s functionality has already been covered in detail elsewhere, so we will instead focus on the mode of compromise and its anti-reversing engineering tactics.

DELIVERY CONTEXT
This particular malware sample began its life as an executable with an RTF exploit. Generally an RTF exploit is a specially crafted file that exploits vulnerabilities in the Rich Text Format parser of an application like Microsoft Word or Adobe Acrobat in order to gain code execution on the victim. The malware can then use this initial code execution to begin its exploit chain. Usually, crafted files are spread as attachments in phishing emails, which was the case in this sample. Once the malware gets code execution on the host it then downloads jazz.exe from the link below.
Source: hxxp://tpreiastephenville.com/jazz.exe
Sha256: a66f989e58ada2eff729ac2032ff71a159c521e7372373f4a1c1cf13f8ae2f0c

PE DESCRIPTION
The binary was compiled with VB6.0 professional/enterprise and so contains normal x86asm with a dependency on msvbvm60.dll. Stage 1 makes specific use of the visual basic runtime DLL to make dll calls to other libraries.
First Stage Shellcode
The first stage shellcode exists within the VB6 portion of the malware, which we’ll refer to as the crypter.  The first stage shellcode exists in the “rentegninger” sub module. The original sub module is then partially overwritten with obfuscated shellcode. The “Remanipulation8” public function is called from Load_Form(). This function manipulates the list of values of the Virtual Function Table returned by the “Me” reference to the form.
Set var_2 = Me

HOW TO GET THE SHELLCODE ENTRYPOINT
Stage 1 overwrites one of the variables in the compiled Visual Basic 6 code to point to an offset in the middle of the “rentegninger” submodule. The pointer is a hard coded integer that is calculated with division and a square root  as shown below.
var_17 = 0x1526C77
new_value = var_17 \ CLng(Sqr((25)))
new_value = 0x43AF4B
 
UTILIZING STRPTR TO ACCESS ADDRESSES
In the code example below the pointer to the Me value points to the beginning of the Virtual Function Table of the class that Me points to. In this case the Class is a Form. The offset 0x2B0 is actually the function “Show”. The pointer to the show function is overwritten by the entry point of the shellcode which is 0x43AF4B. Then you can easily call “Form.Show” and call into your shellcode. An example of this is located in the Appendix.
var_num1 = StrPtr(var_2) + 2B0h
ReplacePtr(var_num1, new_value)


This value is later called in the “Remanipulation8” function as call dword ptr [eax+2B0h]. It treats this call as a method of the Me object. DispCallFunc .
 

STRING-TO-STACK METHOD
The crypter uses a common trick to get the strings that are inline with the assembly onto the stack. When a call is made, the next address gets pushed onto the stack as the return destination address. A disassembler will try to disassemble the string even though it never gets executed.

USING SHELL_NOTIFYICON
The first stage shellcode uses the Shell_NotifyIcon in a non-standard way. It passes an address off the stack that does not resemble a proper PNOTIFYICONDATA struct. The Windows API still processes the events as if they were normal. As you can see below, the Shell_TrayWnd icon is junk data for this process. It is called twice where NIM_ADD and NIM_DELETE are used.



UTILIZING THE PEB LOADER AND DLLFUNCTIONCALL
The first stage shellcode uses a common technique among other Windows shellcode to get a reference to DllFunctionCall by utilizing the Process Environment Block (PEB). The PEB is a data structure provided to every running process, and can be used to gain information about that process such as environment variables, image base addresses and DLL imports. This shellcode contains a PEB loader routine that gets a reference to msvbvm60.dll  and then finds the offset of DllFunctionCall at 0x8D560CEC. Once it has the correct offset to DllFunctionCall, it can then use it to load Windows APIs so that it can make calls to them. More information on the PEB can be found here.
In a nutshell, the PEB is a linked list of offset values and the string names of the desired functions. You can linearly traverse the linked list, check for the desired function and save its offset if found.

DISABLING DATA EXECUTION PREVENTION (DEP)
The function ZwSetInformationProcess can be called with parameters -1 and 0x22 to turn off DEP for the process. DEP was originally intended to prevent programs from executing code on the stack, however DEP can also cause normal programs to crash without any notifications. Giving the program the ability to turn off DEP for itself allows the malware to avoid unknown crashes while also allowing malware authors to execute shellcode explicitly on the Stack. Microsoft Support provides additional details about DEP.



DECODING THE SHELLCODE
The stage 1 shellcode then utilizes JMP ESP to jump into that stack at the offset where the buffer for stage 2 shellcode was allocated. The stage 2 shellcode that was initially loaded onto the stack undergoes an initial pass of XOR decoding with an immediate value of 0x510473D1.


Second Stage Shellcode

SANDBOX EVASION


The stage 1 shellcode executes CPUID to detect if it’s being run in a virtual environment. If it is running in a virtual environment, it exits. If the stage 1 shellcode is not running in a virtual environment, then it continues execution normally. As detailed elsewhere, the malware sets the EAX register to 1, calls CPUID and then checks the 31st bit of the ECX register by applying a bitmask. If the 31st bit is 0 it knows it’s being run in a virtual environment.
Subsequently, the stage 1 shellcode calls the sleep function. Sleeping for prolonged durations of time is one evasion technique used by malware to subvert detection in sandboxed environments which are usually constrained by resource allocation to not run any given sample for longer than some established period of time, such as 30 seconds. Thus for the first 30 seconds of the program’s lifetime, it is benign and might fool some sandboxing environments.

ANTI-DEBUGGING USING NTYIELDEXECUTION
The ntdll function NtYieldExecution or its kernel32 equivalent SwitchToThread function allows the current thread to allocate the rest of the execution time, and allows the next scheduled thread to execute. If no threads are scheduled to execute or when the system is busy (and will not allow such a switch to occur), the ntdll NtYieldExecution() function returns a STATUS_NO_YIELD_PERFORMED (0x40000024) status code, which causes the kernel32 SwitchToThread function to return zero. When an application is being debugged, the act of single-stepping through the code causes debug events to occur and often results in no yield being allowed to occur. However, this is a hopelessly unreliable method of detecting the presence of a debugger because this method will also detect the presence of a thread that is running with high priority. An example of this code can be found here.

for (int i = 0; i < 0x20; i++)
{
         Sleep(0xf);
         if (NtYieldExecution() != STATUS_NO_YIELD_PERFORMED)
         iDebugged++;
}


CHECK FOR ADAPTERS AND WINDOWS
The stage 2 shellcode calls VirtualAllocEX to populate a new memory region with GetAdaptersInfo. It checks the offset +10Ch  of the struct for the Description. It then calls EnumWindows to check if the window has an empty string, most likely an attempt to detect execution within some sandbox.
PERSISTENCE AND PROCESS HOLLOWING
The stage 2 shellcode takes two routes. During the first route, the shellcode sets up persistent mechanisms with schtasks.exe. It then decrypts the payload with Xor and RC4 during the second route, creating a suspended process of itself and then hollows it out with the payload’s contents. Each route is explained below.
Route 1 (Persistence)
The stage 2 shellcode’s first route will acquire the hardcoded strings APPDATA=TEMP=, and copied.exe in order to place a copy of itself in the %APPDATA% and %TEMP% locations as %AppData%\\Roaming\\copied.exe. Once the path is acquired, it will create a scheduled task to copy and run copied.exe using ShellExecuteA.
schtasks.exe" /Create /SC MINUTE /TN "Startup Key" /TR "%AppData%\\Roaming\\copied.exe"
schtasks.exe "/run /tn \"Startup Key\""

If that fails it will try again by adding "\" /RU SYSTEM"
schtasks.exe" /Create /SC MINUTE /TN "Startup Key" /TR "%AppData%\\Roaming\\copied.exe" /RU SYSTEM

It will also set the registry startup run key with:
schtasks.exe /Create /SC HOURLY /MO 12 /TN \"Startup Key\" /TR \"reg add \"HKLM\\Software\\Microsoft\\Windows\\CurrentVersion\\Run\" /v \"\\\"\"Startup Key\"\\\"\" /f /t REG_SZ /d \"\\\"\""

Route 2 (Process Hollowing)
The stage 2 shellcode’s second route focuses on decrypting the executable payload into memory and then hollowing out a child process to execute the payload. “Wee2" is the marker on the stack in the shellcode and in the file that denotes the beginning of  the copy operation. The format is Wee2<length of payload><key>.

Decrypting the Payload with Key
The key is stored in the shellcode after the marker and size in the shellcode. Its length is 0x100h, and is shown below.
00000000: 9944 4203 c046 b4f2 38dd 33ed 0281 473a  .DB..F..8.3...G:
00000010: 1c76 67d8 43bc d9c6 000f 58c2 c9f7 280e  .vg.C.....X...(.
00000020: 9fec 49ac 0bef bb56 8386 7d96 4c2a 4de3  ..I....V..}.L*M.
00000030: 221f 6e80 8e65 e02b 06b8 5f6a cf5c 72b7  ".n..e.+.._j.\r.
00000040: ea51 9354 1197 05ff 892e 843e 53d2 548b  .Q.T.......>S.T.
00000050: 6dc7 b829 940d e6d3 0d60 a913 d604 795f  m..).....`....y_
00000060: f0f9 9afd 183f 0ca7 d4d7 cee7 597b 9e34  .....?......Y{.4
00000070: 7370 bfd1 dfb6 317c 5709 b0bb 20ad c308  sp....1|W... ...
00000080: f7a2 e461 62e8 1250 da3b d54b a423 a5dc  ...ab..P.;.K.#..
00000090: be18 c536 e51a 3724 5eb1 fa20 2755 cab0  ...6..7$^.. 'U..
000000a0: 414a eb0a 6990 5df8 e1e4 dbf4 aacc ef41  AJ..i.]........A
000000b0: c4c1 10de ecc3 3ecd 645a 01c8 2dfe d015  ......>.dZ..-...
000000c0: 48f3 f1b2 b339 63a1 2b8c 269c f530 f6e9  H....9c.+.&..0..
000000d0: cb25 1687 366b 8875 af02 0771 78a6 1bbd  .%..6k.u...qx...
000000e0: 4e9b 3c5b bae1 ae49 3235 2c45 fbd9 fc92  N.<[...I25,E....
000000f0: 15ce 1d2f 3d14 8f1e b567 5219 7e4f 2166  .../=....gR.~O!f

The stage 2 shellcode uses the 0x100 sized byte key to xor the Loki-Bot payload of 0x34801 size then uses the same key to RC4 decrypt the product of the xor operation.

The shellcode then calls CreateProcessW to create a process of itself in suspended mode. It uses NTCreateFile, NTWriteVirtualMemory, NTUnMapViewofSection for process hollowing on the newly created process which contains the Loki-Bot payload. NtGetContextThread and NtSetContextThread and NtSetContextThread resume the process. The parent process terminates allowing the child to run as an orphan process. Because the Loki-Bot payload has already been reviewed by many researchers, we did not post the details about this malware.

Conclusion
There are a few key aspects to this crypter and its behaviour that make it fishy, including its crafty implementation of the VB6 runtime in shellcode, and use of anti-reverse engineering techniques and process hollowing. First, VB6 and the VB6 run time are rather old. While there are numerous binary distributions of software in the wild that were built with VB6 enterprise, it is still suspicious. Other suspicious activities include disabling its own DEP and checking if it’s being virtualized. Lastly, the crypter makes calls to the Windows API with malformed structs (i.e. the lack of an image for Shell_NotifyIcon). The combination of all of these suspicious activities could signal to a sensor like Endgame MalwareScoreTM that the program is up to no good, allowing us to stop it before the final execution occurs.  
As for the future, we are likely to see more samples using legacy run times and features. Judging from this sample, a performant Visual Basic 6 crypter has recently been distributed in the wild. It seems natural that in the future its capabilities will improve and the volume of distribution will increase with continued black market adoption.

Appendix: Stage 1 Code Replication
After careful analysis, we were able to reproduce the method of Stage 1 shellcode execution in VB6. The code below will only display an empty message box.

VB6 CODE
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" _
    (ByRef lpvDest As Any, _
     ByRef lpvSrc As Any, _
     ByVal cbLength As Long)

Private Sub Form_Load()
    Me.Hide
    Dim lngRc As Long
    CopyMemory lngRc, Me, 4
    CopyMemory lngRc, ByVal lngRc, 4
    CopyMemory ByVal (lngRc + 688), 4202169, 4
    Me.Show
End Sub

SHELLCODE
E9 88 00 00 00 59 E9 8E 00 00 00 5A E8 0C 00 00 00 50 6A 00 6A 00 6A 00 6A 00
FF D0 C3 64 A1 30 00 00 00 8B 40 0C 8B 40 14 8B 00 8B 58 28 BE 4C 00 53 00 46
39 33 75 F1 81 7B 04 56 00 42 00 8B 70 10 56 8B 5E 3C 36 8B 34 24 01 DE 8B 5E
78 36 8B 04 24 01 D8 89 C6 83 C6 28 AD 85 C0 74 FB 03 04 24 BB 55 8B EC 83 39
18 75 EF 81 78 04 EC 0C 56 8D 75 E6 5B 31 DB 53 53 53 54 6A 00 81 04 24 00 00
04 00 52 51 54 FF D0 83 C4 1C C3 E8 73 FF FF FF 75 73 65 72 33 32 00 E8 6D FF
FF FF 4D 65 73 73 61 67 65 42 6F 78 41 00

ASSEMBLY
[SECTION .text]
global Start
Start:
    jmp     getdll
nextstring:
    pop ecx
    jmp     getstring
getapi:
    pop     edx ;put string in ebx
    call    loadapi
    push    eax ;get MessageBoxA
    push    0
    push    0
    push    0
    push    0
    call    eax
    retn
loadapi:
    mov     eax, [fs:0x30] ;Get the address of PEB
    mov     eax, [eax+0x0C] ;Get the address of PEB_LDR_DATA
    mov     eax, [eax+0x14] ;Get InMemoryOrderModuleList
loop1:
    mov     eax, [eax]
    mov     ebx, [eax+0x28]
    mov     esi, 0x53004C ;L S
    inc     esi ;M S for MSVBVM60.DLL
    cmp     [ebx], esi
    jnz     loop1
    cmp     dword [ebx+0x4], 0x420056 ;V B for MSVBVM60.DLL
    mov     esi, [eax+0x10]
    push    esi
    mov     ebx, [esi+0x3C]
    mov     esi, [ss:esp] ;<msvbvm60.Ordinal958>
    add     esi, ebx
    mov     ebx, [esi+0x78]
    mov     eax, [ss:esp] ;<msvbvm60.Ordinal958>
    add     eax, ebx
    mov     esi, eax
    add     esi, 0x28
loop2:
         lodsd
         test    eax, eax
         jz      short loop2
         add     eax, [esp]
         mov     ebx, 0x83EC8B55
         cmp     dword [eax], ebx
         jnz     short loop2
         cmp     dword [eax+0x4], 0x8D560CEC ;DllFunctionCall
         jnz     short loop2
         pop     ebx
         xor     ebx, ebx
         push    ebx
         push    ebx
         push    ebx
         push    esp
         push    0
         add     dword [esp], 0x40000
         push    edx ;MessageBoxA
         push    ecx ;user32
         push    esp
         call    eax ;DllFunctionCall
         add     esp, 0x1C
         retn
getdll:
    call nextstring
         db 0x75 ;u
         db 0x73 ;s
         db 0x65 ;e
         db 0x72 ;r
         db 0x33 ;3
         db 0x32 ;2
         db 0x00
getstring:
    call getapi
         db 0x4D ;M
         db 0x65 ;e
         db 0x73 ;s
         db 0x73 ;s
         db 0x61 ;a
         db 0x67 ;g
         db 0x65 ;e
         db 0x42 ;B
         db 0x6F ;o
         db 0x78 ;x
         db 0x41 ;A
         db 0x00


Source:
https://www.endgame.com/blog/technical-blog/what-year-it-vb6-payload-crypter






Linear Transforms

$
0
0
This app shows mapping of a rectangular image onto a quadrilateral, circle, cylinder, cone and a sphere. This implementation is made by Robert Rayment (I think is a mathematician if I am not mistaken - he influenced a few generations of programmers with his implementations). 


Download from PSC
Download from ME








Viewing all 181 articles
Browse latest View live