Comprehensive CAN monitor for Windows® and its add-ins: Plotter, CANdb Import, Instruments Panel, and J1939
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 09:02
Hello everyone,
I started to use PCAN Explorer 5 a couple of months ago and right now I'm trying to create VBS Macros to test with some projects.
I've already written successfully some Macros to transmit CAN messages.
Now I wanted to check out if there are received messages from a certain CAN-ID and at last read their data.
I've already managed to check if there are some messages from that CAN-ID and to count them, but I can only read the data from the last one.
How can I read the data of all received messages from a CAN-ID?
Your help would be appreciated.
Thank you in advance!
Here is my code at the moment:
Code: Select all
Function canerrors()
Dim msgs, errors, cont, cont2, a, b
Set msgs = Connections.ReceiveMessages
cont = msgs.FindID(&H083).Count
If cont = 0 Then
MsgBox "There are no CAN errors!", vbOKOnly + vbInformation, "CAN Test"
Exit Function
Else
Set errors = msgs.FindID(&H083).Item(1)
cont2 = errors.EventCount
MsgBox "There are some CAN errors!" & Chr(13) & "(" & cont2 & " errors)", vbOKOnly + vbExclamation, "CAN Test"
With errors
a = Hex(.Data(0))
b = Hex(.ID)
End With
MsgBox a & "," & b
End If
End Function
-
PEAK-Support
- Sales & Support

- Posts: 1646
- Joined: Fri 10. Sep 2010, 19:34
Post
by PEAK-Support » Tue 19. May 2015, 09:54
We do not understand what exact you like to do. If you want to get all CAN-ID´s with ID 0x083 and print out the DataByte 0 , you need to do this in a loop for Online (live) capture.
If you like to get this info out of recived (in the past) CAN Messages, plrease use the Tracer function.
In the receive List you will only find the latest CAN Databytes of a received ID , and the counter how often the ID was received - no history Info of DataBytes from the past where stored.
--------------------------------
PEAK-System Technik
Technical Support Team
support[at]peak-system.com
-------------------------------
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 10:10
Hello U.Wilhelm,
Thank you for your quick answer.
At the moment what I'm trying to do is the following:
1) First I send some messages to the Bus.
2) At the end of the transmission, I want:
2a) To check if there are some received messages with a certain CAN-ID (e.g. 0x083) --> (I've already achieved that.)
2b) To count how many messages did I receive from that CAN-ID --> (I've also done that)
2c) And finally to read all data from that received messages. --> This is where I'm stuck at the moment.
Could you help me out?
-
PEAK-Support
- Sales & Support

- Posts: 1646
- Joined: Fri 10. Sep 2010, 19:34
Post
by PEAK-Support » Tue 19. May 2015, 11:03
OK, you like to start your Macro , and want to send one spezific CAN ID.
After that you will wait for the specific answer (ID) and loop until...?!?
what is your end condition ?
Here a simple Macro which wait for specific Data
Code: Select all
'------------------------------------------------------------------------------
'FILE DESCRIPTION:RecvCAN Data
'------------------------------------------------------------------------------
Sub RecvCANData()
'DESCRIPTION: Read CAN Data - see if in a defined CAN Msg data one Bit is set
' To view the output messages of this macro, open the Output Window and
' select the "Macro" tab
Dim Myclient, MyConn
Set MyClient = CreateObject("Pcan3.PCANClient")
MyClient.Name = "RecvCANDataMacro"
If Connections.Count > 0 And Connections(1).Protocol = peProtocolCAN Then
' Connect to the same Net that the first connection in the
' current project uses
Dim obj
Set obj = Connections(1).CommunicationObject
MyClient.Device = obj.Parent.Device
Set MyConn = MyClient.Connections.Add(obj.NetName)
Else
' Connect to the default "TestNet"
Set MyConn = MyClient.Connections.Add("TestNet")
End IF
If MyConn.IsConnected = False Then
MsgBox "Cannot connect to Net"
Exit Sub
End If
' MyConn.RegisterMsg &H000, &H800, False, False
' MyConn.RegisterMsg &H00000000, &H1FFFFFFF, True, True
' MyConn.RegisterMsg &H600, &H1FFFFFFF, True, True
PrintToOutputWindow "Start the Read...."
i = 0
Dim RcvMsg
Set RcvMsg = MyClient.Messages.Add
Do
Do While not RcvMsg.Read
' Wait for a received message
Wait(10) ' Prevent 100% CPU load
Loop
If RcvMsg.LastError = pcanErrorOk Then
If RcvMsg.DLC > 0 Then ' Yes, >0 DLC ist OK
If RcvMsg.Data(0) AND &h80 Then
PrintToOutputWindow "Received CAN ID: " & CStr(RcvMsg.ID)
PrintToOutputWindow "Data0 is set to 0x80"
i = i + 1
End If
End If
End IF
Loop While RcvMsg.ID <> &H001 ' Stop when receiving ID 0x001
PrintToOutputWindow "Finished, " & CStr(i) & " messages 0x80 in Data0 received !"
End Sub
--------------------------------
PEAK-System Technik
Technical Support Team
support[at]peak-system.com
-------------------------------
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 11:26
I start the Macro with an InputBox asking user to select 1 of 2 possibilities and then another InputBox asks for how many times wants the user to repeat that process (variable 'cont').
Supposing the user chooses Option 1 and wants to repeat that for 10 times, the Macro will send 10 times a specific message, for example this:
Code: Select all
For i = 1 to cont
movement &HBE,&H01,&H1E,&H0A,msg
Next
Function movement(a,b,c,d, msg)
Wait 250
With msg
.Connection = Connections(1)
.ID = &H18B
.DLC = 8
.Data(0) = a
.Data(1) = b
.Data(2) = c
.Data(3) = d
.Write 0
End With
End Function
After that test is complete, I want to see whether some messages from a certain CAN-ID (e.g. 0x083) were received or not during the transmission, how many times and what data had come with those messages?
So the stopping criteria is just the number of times the user wants to repeat the message sending.
-
PEAK-Support
- Sales & Support

- Posts: 1646
- Joined: Fri 10. Sep 2010, 19:34
Post
by PEAK-Support » Tue 19. May 2015, 12:51
Hi, try this:
Code: Select all
'------------------------------------------------------------------------------
'FILE DESCRIPTION: Keine Beschreibung angegeben.
'------------------------------------------------------------------------------
Sub SimpleProtocol()
'DESCRIPTION: This MACRO send a request to a ECU and wait for n-Times for any answer from the Bus
' The User could use the Input Box to define the value of the retry counter
'
' To view the output messages of this macro, open the Output Window and select the "Macro" tab
Dim UseConn, conn
' Find the first enabled connection in the project that uses the CAN protocol
Set UseConn = Nothing
For Each conn In Connections
If conn.IsEnabled And conn.Protocol = peProtocolCAN Then
Set UseConn = conn
Exit For
End If
Next
If UseConn Is Nothing Then
MsgBox "This Project does not contain any enabled CAN connections!"
MsgBox "Please check your Connection Box if your Hardware is connected."
Exit Sub
End If
' Create a new client and connect it to the same Net that the
' found connection uses
Dim MyClient, PcanConn
Set MyClient = CreateObject("PCAN3.PCANClient")
MyClient.Name = "SimpleProtocol"
MyClient.Device = UseConn.Device
Set PcanConn = MyClient.Connections.Add(UseConn.CommunicationObject.NetName)
' Set Filter, so that we only receive in this script ID from 0x083 to 0x18B
PcanConn.RegisterMsg &H083, &H18B, False, False
' i ist the counter how often we receive the ID 0x083
i = 0
' count is the loop counter - changed by a input box value
count = 0
Dim RcvMsg 'we use this structure to Receive CAN Frames
Dim SendMsg 'we use this structure to Transmit CAN Frames
Set RcvMsg = MyClient.Messages.Add
' Now create and initialize a new transmit message
Set SendMsg = MyClient.Messages.Add
timestamp = MyClient.GetSystemTime
PrintToOutputWindow "Macro running"
strcount = InputBox("Loop Counter", "SimpleProtocol")
If strcount <> "" Then
count = CLng(strcount)
Else
count = 5
End If
' Here we start!
' Now we add the needed DataBytes to the CAN Request Message
' For example Byte0=0x10 and DatByte1=0x11, ID=0x83, DLC = 2, STD CAN Frame (11Bit)
With SendMsg
.ID = &H083
.DLC = 2
.MsgType = pcanMsgTypeStandard
.Data(0) = &H10
.Data(1) = &H11
End With
' here we start the Loop! -- running until the conter reached the limit
Do
' Send the defined CAN ID - also could be done in a SUB - thats up to you
SendMsg.Write PcanConn, timestamp
PrintToOutputWindow "CAN ID send"
' Wait for a received message
' sleep 5 milisec. to give the CAN Bus a chance to transmit the ID and the ECU to answer :-)
Wait(5)
if RcvMsg.Read Then ' Read next CAN Date (keep in mind Filter is set!) from Queue
' check if CAN Frame received
If RcvMsg.LastError = pcanErrorOk Then
' Check if ID = 0x083
If RcvMsg.ID = &H083 Then
' print out text
PrintToOutputWindow "ID 0x083 Received !"
i = i + 1
' copy the received Databytes to the Output Window
for a=0 to RcvMsg.DLC
PrintToOutputWindow "Data" & CStr(a) & ": " & CStr(RcvMsg.Data(a))
next ' next a
' to stop the loop we set count now to 1 - so next decremt it will be 0
count = 0
End If ' Endif ID OK
End IF ' Endif no Error
End If ' Endif Read OK
' Loop until Message ID 0x101 receiced
count = count -1
Wait(250) ' here we wait 250ms until we try the next resend - without a delay at this point, all CAN Frames will be send within mSeconds
Loop While count > 0
PrintToOutputWindow "Finished, " & CStr(i) & " messages with ID 0x083 received !"
End Sub
--------------------------------
PEAK-System Technik
Technical Support Team
support[at]peak-system.com
-------------------------------
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 13:09
Thanks once again U.Wilhelm!
I'll try that and then I post here some feedback.
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 16:12
Hi U.Wilhelm!
I've already tried your script and after some minor changes it has worked fine, just like I wanted!
Thank you very much for your precious support!
-
jnota
- Posts: 20
- Joined: Mon 18. May 2015, 17:32
Post
by jnota » Tue 19. May 2015, 16:47
Hi again,
Now I've noticed that sometimes the script doesn't "catch" all the errors, comparing to the Receive Window in PCAN Explorer. It seems like the messages are sent too fast for what the script can take...
Like I said, that doesn't happen always, just sometimes.
What can I do? Should I increase the wait time? I've already tried (I changed Wait (5) to Wait(10)) , but it doesn't work.
I have also a delay before every message's sending (250ms), immediately after the "Do" instruction.
-
PEAK-Support
- Sales & Support

- Posts: 1646
- Joined: Fri 10. Sep 2010, 19:34
Post
by PEAK-Support » Tue 19. May 2015, 16:56
The queue will not miss any message, and the Client you have created with the script have it´s own queue. Simply open the PCAN-Status Panel while your macro is running - you will see a second client connected side by side to the PCAN-Explorer Send/Receive connection.
Does your external CAN node sending the specific ID (0x083) only once when you send out your request, or could it be that it send out more than once? The code i post read one answer from the receive queue if you send a request. (Ping/Pong) You need to extend the read function inside the loop in that way, that it reads until there is no other answer in the queue.
--------------------------------
PEAK-System Technik
Technical Support Team
support[at]peak-system.com
-------------------------------