andrewjfox

Members
  • Content Count

    68
  • Joined

  • Last visited

Community Reputation

0 Neutral

About andrewjfox

  • Rank
    Member

Profile Information

  • Gender
    Male
  1. Hi, I've got a query regarding memory array and sharing between sequences running in seperate threads. I'd like to have Sequence1 putting data into an array, and Sequence2 pulling it out ie FIFO. I was thinking of implementing a fifo array with head and tail indexes where the "putting" sequence uses the head and the "pulling" sequence uses the tail index. 1. Is it safe to use the arrays like this, are they thread-safe? 2. I haven't seen a builtin "fifo" structure so will have to implement in code which I've done many times but not in DF. Do you have any tips/pitfalls to watch out for? Background info My application involves pulling data from a remote TCP device, putting a time stamp on it and putting it into an array, for another sequence to process. I need the putting seq to be fast since it's the one putting time stamps on incoming data and I want them to be as real time as possible. The processing sequence does a bunch of sorting, processing and manipulating then stores the required data to file, so this can be a bit slower. Currently I'm using a basic semaphore flag to control which sequence gets access, however I don't think it's the most effective way since it means the putting sequence may have to wait for the processing sequence to relinquish the flag. Regards Andrew
  2. andrewjfox

    Comm Objects

    Thanks, that seems to work bit better. When I close the connection the only error is when I try to call .Write later which makes sense. I do still have a problem in regards modifying the port parameters When I instatiate the port object MyPort[index] = new(CCommEthernet) then assign values MyPort[index].Address = "127.0.0.1" MyPort[index].Port = 1515 then assign port to device pDevice.PortObject = MyPort[index] This all works ok first time. If I want to change port values do I change the port object then reassign MyPort[index].Port = -1 then pDevice.Portobject = MyPort[index] OR change device values directly pDevice.Port = -1 When I change Port to -1 to close connection then it doesn't assign value to device eg MyPort[index].Port = -1 pDevice.Portobject = MyPort[index] ? pDevice.Port // displays 1515, value of port hasn't changed versus pDevice.Port = -1 ? pDevice.Port // displays 4294967295 I had thought that assigning port object to the device is just like assigning a pointer, rather than a param copy, so any changes to the port object would be reflected in the device params. Regards Andrew
  3. andrewjfox

    Comm Objects

    Sorry to hassle you guys again, but you're suggestions aren't working and I'm still having trouble understanding what's going on with objects and InitComm() Have been doing some testing to try and demonstrate what I'm seeing and have attached the following EchoServer.exe Echo server is a basic TCP server on ports 1515 & 1516 that displays messages when clients connect/disconnect and echos any data received back to client Test.ctl - This is my test doc, it opens TCP connections using dynamic comm devices to local 127.0.0.1 and ports 1515 & 1516 You'll see that towards the end I have setup 2 options for closing the connection however, OPTION = 0, trying to clear TCP address by writing to MyDevice.iDevice.Address = "", however this approach throws an error when it gets to InitComm() which should be closing the connection. From looking at the server console it does appear to close the connection before throwing the error OPTION = 1, clear the port object address, then assign the port object to the device, this has no errors, but doesn't close the connection. When I write to port after it is suppossedly closed, the echo works fine, almost as if it re-opens the connection even though the address should be "". I'm doing all the things you've suggested in regards referencing objects using pointers, and clearing the port address before calling InitComm() to close the connection, but either approach I take doesn't work correctly Please have a look and let me know if the problems is something I've done, or don't understand or other. Test.zip Test.zip
  4. andrewjfox

    Comm Objects

    This brings us back to the original post, when I do this the function can't be found See above for more details but basically I have several dynamically created objects MyDevice[], each containing a device object, iDevice which is instatiated using the OnCreate function of the parent object, iDevice = new(CComDevice). The whole object is then referenced using a pointer. private pDevice = MyDevice[index] then calling the InitComm function using pDevice.iDevice.InitComm(), which fails with error C1000 Channel or function not found calling MyDevice[index].iDevice.InitComm() works ok, however you suggest that the indexing is wrong, please explain further. I've changed the application in the (numerous) field systems so that it's using the indexing method MyDevice[index].iDevice.InitComm(), however from the content of this thread I'm not confident that this is working correctly either, it's just not throwing exceptions. I'm having comms problems in the field but so far I've been unable to determine if it's DF comms issues or the physical devices. I've already tested that InitComm isn't failing because of the physical device, there must be a software issue, perhaps something to do with the pointer referencing. Andrew
  5. andrewjfox

    Comm Objects

    My apologies, I misunderstood the intention of your post #6. No, in the actual application, all of the devices are created dynamically. In the test doc (comms_test.ctl) I'm opening connections to the same, real, devices as in the actual application. My concern is not that one or the other method of referencing object functions doesn't work, but that it appears to be inconsistent, sometimes working, but not others, and I don't see how this is device dependent since a function (any function) can only succeed or fail after it's been called. It shouldn't throw an exception before attempting to call the function, on the expectation that the device comms may or may not fail, should it? Which method will work 100% of the time - indexed objects ie MyDevice[index].Device.InitComm() - or can I use pointer reference such as pDevice = MyDevice[index].Device, and pDevice.InitComm()
  6. andrewjfox

    Comm Objects

    Have done a few quick tests, as suggested. Created blank document and new devices using configuration wizard Device1Ctrl, Device1Radio, Device2Ctrl and Device2Radio Tried opening and closing first using Device.Device1Ctrl.InitComm(), etc then using private pDevice = Device.Device1Ctrl and pDevice.InitComm() following is output from attached test doc "comms_test.ctrl". Opening connections Closing connections Reopening connections with ptrs 09/08/12 13:43:56.941 C1000 Channel or function not found: startup Line 44 - Uncaught error in sequence startup using pDevice.InitComm(), at least on my system, throws an error. If this is the case then it might also explain why I am getting irregular errors when calling .Read & .Write functions using ptrs. It works sometimes, but not others. Up till know I have been assuming the end devices are causing all the problems. If ptrs only work in some cases, I need to know the guidelines for usage. Please I need a practical fix/workaround asap, . Eagerly awaiting reply, Andrew comms_test.ctl
  7. andrewjfox

    Comm Objects

    -bug in parsing ? Is it a problem using calculations in indexes in general, or only for objects? Can I use a calculated variable to solve eg private index = readerindex*2 + CTRL_PORT, then MyDevice[index]. How do I assign the object pointer if there is a problem with the indexing ie pDevice = MyDevice[???] -the devices are TCP, does initcomm attempt to open the TCP connection, and will it fail gracefully if it can't make the connection? I will put a test file together to try and isolate the problem as suggested Andrew
  8. andrewjfox

    Comm Objects

    Hi, after some more testing I'm pretty sure the problem occurs at the .InitComm() line As above I have 8 device objects instantiated thusly; class DeviceObj local iDevice local RxBuff local State function OnCreate() iDevice = new(CCommDevice) State = DEVICE_STATE_CLOSED endfunction endclass global MyDevice global MyPort NumReaders = 4 for(private i=0,i<NumReaders,i++) MyPort[i*2 + CTRL_PORT] = new(CCommEthernet) MyDevice[i*2 + CTRL_PORT] = new(DeviceObj) MyPort[i*2 + RADIO_PORT] = new(CCommEthernet) MyDevice[i*2 + RADIO_PORT] = new(DeviceObj) OpenConnection(i) // additional stuff here endfor [/CODE] [CODE] function OpenConnection(ReaderIndex) private pDevice private pPort // try pDevice = MyDevice[ReaderIndex*2 + CTRL_PORT] //if(pDevice.State == DEVICE_STATE_CLOSED) pPort = MyPort[ReaderIndex*2 + CTRL_PORT] pPort.Address = strAddressBase + DoubleToStr(DeviceAddress[ReaderIndex]) pPort.Port = CPORT pPort.Timeout = 1000 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + CTRL_PORT] pDevice.iDevice.ProtocolName = "NULL Protocol" pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_OPEN //endif pDevice = MyDevice[ReaderIndex*2 + RADIO_PORT] //if(pDevice.State == DEVICE_STATE_CLOSED) pPort = MyPort[ReaderIndex*2 + RADIO_PORT] pPort.Address = strAddressBase + DoubleToStr(DeviceAddress[ReaderIndex]) pPort.Port = RPORT pPort.Timeout = 1000 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + RADIO_PORT] pDevice.iDevice.ProtocolName = "NULL Protocol" pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_OPEN //endif // catch() // Event.AddValue(Format("Error: Rdr%02d, ",ReaderIndex)+strLastError) // endcatch endfunction [/CODE] when I try to close the connection using following I get an error at the InitComm(). (I stepped through the sequence and the error definitely occurs when trying to execute the InitComm() line) [CODE] //function CloseConnection(ReaderIndex) private ReaderIndex = 1 private pDevice private pPort // try pDevice = MyDevice[ReaderIndex*2 + CTRL_PORT] pPort = MyPort[ReaderIndex*2 + CTRL_PORT] pPort.Address = "" pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + CTRL_PORT] ? MyDevice[].iDevice.Address ? MyDevice[].iDevice.Port pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_CLOSED pDevice = MyDevice[ReaderIndex*2 + RADIO_PORT] pPort = MyPort[ReaderIndex*2 + RADIO_PORT] pPort.Address = "" pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + RADIO_PORT] pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_CLOSED // catch() // Event.AddValue(Format("Error: Rdr%02d, ",ReaderIndex)+strLastError) // endcatch //endfunction [/CODE] if, however, I replace the line pDevice.iDevice.InitComm() with MyDevice[ReaderIndex*2 + CTRL_PORT].iDevice.InitComm() it works ok. I know that the objects can be funny about using brackets on both sides, is it possible that for object function calls I need to use the actual object, MyDevice[2].iDevice.InitComm() rather than a pointer like pDevice.iDevice.InitComm() Regards Andrew
  9. andrewjfox

    Comm Objects

    In the sequence line numbering, line 15 is the initComm line. Is this one of those instances where, because I'm using objects, the error message is not pointing to where I think it's pointing? I had also meant to ask about including port object in my MyDevice object but accidentally submitted the post before finishing. As I started to mention, I tried including the port object in MyDevice object class DeviceObj
  10. andrewjfox

    Comm Objects

    Hi , I've been using objects for ports and devices in an existing project but am still getting some behaviour which I don't understand I am trying to close and -reopen a ethernet connection as follows //Instatiate objects, and open connections define CTRL_PORT = 0 define RADIO_PORT = 1 class DeviceObj local iDevice local RxBuff local State function OnCreate() iDevice = new(CCommDevice) State = DEVICE_STATE_CLOSED endfunction endclass global MyDevice global MyPort for(private i=0,i<MAX_READERS,i++) MyPort[i*2 + CTRL_PORT] = new(CCommEthernet) MyDevice[i*2 + CTRL_PORT] = new(DeviceObj) MyPort[i*2 + RADIO_PORT] = new(CCommEthernet) MyDevice[i*2 + RADIO_PORT] = new(DeviceObj) OpenConnection(i) endfor [/CODE] // functions to open & close connections [CODE] function OpenConnection(ReaderIndex) private pDevice private pPort try pDevice = MyDevice[ReaderIndex*2 + CTRL_PORT] if(pDevice.State == DEVICE_STATE_CLOSED) pPort = MyPort[ReaderIndex*2 + CTRL_PORT] pPort.Address = strAddressBase + DoubleToStr(DeviceAddress[ReaderIndex]) pPort.Port = CPORT pPort.Timeout = 1000 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + CTRL_PORT] pDevice.iDevice.ProtocolName = "NULL Protocol" pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_OPEN endif pDevice = MyDevice[ReaderIndex*2 + RADIO_PORT] if(pDevice.State == DEVICE_STATE_CLOSED) pPort = MyPort[ReaderIndex*2 + RADIO_PORT] pPort.Address = strAddressBase + DoubleToStr(DeviceAddress[ReaderIndex]) pPort.Port = RPORT pPort.Timeout = 1000 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + RADIO_PORT] pDevice.iDevice.ProtocolName = "NULL Protocol" pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_OPEN endif catch() Event.AddValue(Format("Error: Rdr%02d, ",ReaderIndex)+strLastError) endcatch endfunction function CloseConnection(ReaderIndex) private pDevice private pPort //try pDevice = MyDevice[ReaderIndex*2 + CTRL_PORT] pPort = MyPort[ReaderIndex*2 + CTRL_PORT] pPort.Address = "" pPort.Port = 0 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + CTRL_PORT] pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_CLOSED pDevice = MyDevice[ReaderIndex*2 + RADIO_PORT] pPort = MyPort[ReaderIndex*2 + RADIO_PORT] pPort.Address = "" pPort.Port = 0 pDevice.iDevice.PortObject = MyPort[ReaderIndex*2 + RADIO_PORT] pDevice.iDevice.InitComm() pDevice.State = DEVICE_STATE_CLOSED //catch() // Event.AddValue(Format("Error: Rdr%02d, ",ReaderIndex)+strLastError) //endcatch endfunction [/CODE] When I call the CloseConnection function I get an error at the InitComm() function CloseConnection(0) C1000 Channel or function not found: CloseConnection Line 15: Line 1 My understanding is that the InitComm() call should be successful regardless of whether connection is open /closed. Do you have any ideas for me to try? Also I tried including the port object in my device object class DeviceObj local iDevice local RxBuff local State function OnCreate() iDevice = new(CCommDevice) State = DEVICE_STATE_CLOSED endfunction endclass Regards Andrew
  11. andrewjfox

    Variable AddValue vs Variable[0]

    Thanks, That seems to work well. Just to let you know, I've also had problems with ClearBit function messing up timestamped data // My array is timestamped as previous post MyArray[0][0] = ClearBit(MyArray[0][0],7) // doesn't work as expected // make sure return data is timestamped fixes problem (long winded but works) MyArray[0][0] = InsertTime(ClearBit(MyArray[0][0],7), MyArray.Time[0], 0) Thanks Andrew
  12. andrewjfox

    Variable AddValue vs Variable[0]

    I've written a small sequence to test variable history and see what is happening. I must admit it's not what I expected. (BTW I'm using latest version 5.87a) private MyArray MyArray.AddValue(InsertTime({{128,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19}}, SysTime(), 0)) ? MyArray Delay(1) MyArray.AddValue(InsertTime({{129,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19}}, SysTime(), 0)) ? MyArray Delay(1) MyArray.AddValue(InsertTime({{130,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19}}, SysTime(), 0)) ? MyArray Delay(1) MyArray.AddValue(InsertTime({{131,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19}}, SysTime(), 0)) ? MyArray for(private i = 0, i<4, i++) ? Format("[%d], %s, %d ",i,FormatTime(MyArray.Time[i]),MyArray[i][0]) endfor // all good till here MyArray[0][0] = ClearBit(MyArray[0][0],7) ? MyArray ? MyArray.Time // clearing the bit not only clears the whole array + history, but messes the timestamp as well [/CODE] Everything seems ok until I try writing to one of the array elements, then all of the data (inc history) gets wiped and the time stamps get messed up. Would greatly appreciate you pointing out my problem, if it's a code issue, or alternatively advise a better solution. Regards Andrew
  13. Hi, I'm having some trouble with the various data types. Although variables, channels and vchannels work similarly (in theory) I'm finding certain subtle differences and can't get the right type for what I want. application: I'm storing arrays as they come in over a network to a variable for later processing. eg Data.AddValue({{128,1,3,5,7}}) Data.AddValue({{129,2,4,6,8}}) Data = {{129,2,4,6,8},{128,1,3,5,7}} then in processing loop the code looks for data with bit 7 set (data dirty bit) in first element, and clears this bit when data has been processed. if(TestBit(Data[0][0],7)) Data[0][0] = ClearBit(Data[0][0],7) // do some processing on Data endif [/CODE] The processing loop also uses the timestamp of each array, Data.Time[0], as part of the processing Problem: - If Data is V type, then AddValue sets the time of all previously added arrays in history to the same value, so I can't use the timestamps to process the data - If Data is channel, then trying to change an existing value (Data[0][0]) is the same as AddValue, so adds new entry with incorrect data, instead of changing the existing data at [0][0] - If data is variable then, again, trying to change a single element Data[0][0] stuffs up the entire history I'd like to be able to add arrays to a channel/variable, and be able to go through the history and change individual elements. Is this possible using the functions AddValue etc, or do I need to manually manipulate a standard array? I only want a history of about 100 arrays Regards Andrew
  14. andrewjfox

    P-ModbusTCP 0013: Port locked

    Something weird is happening. I started making changes as suggested and first set all the timing to 0, except 1 input register which I left at 1sec. Now I'm still getting port locked message, once a second. I haven't implemented the sequence read of other channels yet so the only device access is this single channel. Is it possible there is a problem in the MB device driver. I'm using latest 5.87 with builtin MB TCP device. I've included the ctl doc if it's worth you checking it out. Andrew 0038-008.ctl
  15. andrewjfox

    SFTP - Solution

    Another good SFTP solution is CoreFTP Client LE and mini SFTP server (both free). www.coreftp.com The mini server is simple to setup and use and works well (I've tested using Filezilla as client). Andrew