paulscherrerinstitute / pcaspy

Portable Channel Access Server in Python
BSD 3-Clause "New" or "Revised" License
32 stars 24 forks source link

pysh.py example in the tutorial does not work (caput'ed value is garbage). #73

Closed CarlosCumming closed 1 year ago

CarlosCumming commented 2 years ago

The pysh.py example in the pcaspy tutorial fails on both of my Linux machines (Ubuntu, centos7) using both python2 and python3, and epics 3.15.9. The following code produces this output with a "caput MTEST:COMMAND date":

$ ./pysh.py ('WRITE', 'COMMAND', '\xda')

This code is from the example stripped down to it's bare minimum, including removing the async example code.

#!/usr/bin/env python

import time
import sys
from pcaspy import Driver, SimpleServer

prefix = 'MTEST:'
pvdb = {
    'COMMAND' : {
        'type' : 'char',
        'count': 128,
    },
}

import math
class myDriver(Driver):
    def __init__(self):
        Driver.__init__(self)
        self.tid = None

    def write(self, reason, value):
        print("WRITE", reason, value)
        self.setParam(reason, value)
        return True

if __name__ == '__main__':
    server = SimpleServer()
    server.createPV(prefix, pvdb)
    driver = myDriver()

    while True:
        # process CA transactions
        server.process(0.1)
xiaoqiangwang commented 2 years ago

For PVs of char array, use the -S switch of caget/caput command.

$ caput -S MTEST:COMMAND "a long command to run"
Old : MTEST:COMMAND 
New : MTEST:COMMAND a long command to run
CarlosCumming commented 2 years ago

Thanks! That worked!

However, I've used epics, including caput for over a decade, including caput'ing strings (but never obviously, pcasspy). I've never had to use the -S switch, and the example is still wrong.... as the caput in the example also doesn't use -S.

I'm curious why it's needed in this instance???

thx, tom.c

On Thu, Jan 6, 2022 at 10:14 AM Xiaoqiang Wang @.***> wrote:

For PVs of char array, use the -S switch of caget/caput command.

$ caput -S MTEST:COMMAND "a long command to run" Old : MTEST:COMMAND New : MTEST:COMMAND a long command to run

— Reply to this email directly, view it on GitHub https://github.com/paulscherrerinstitute/pcaspy/issues/73#issuecomment-1006903370, or unsubscribe https://github.com/notifications/unsubscribe-auth/ALBV2O2TQXZTGL57OQPGAD3UUXZZTANCNFSM5LNDUUGA . Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub.

You are receiving this because you authored the thread.Message ID: @.***>

xiaoqiangwang commented 2 years ago

For string type, channel access limits the string length to 40. They are reported as _DBFSTRING by cainfo command. In EPICS IOC database, they can be the VAL field of stringin/stringout records, or DESC, INP, OUT fields to name a few. In pcaspy program, they are PVs configured as {"type": "string"}.

To work with long strings, use char arrays. They are reported as _DBFCHAR with the count as the string length. In EPICS IOC database, they are mostly configured as waveform records with FTVL=CHAR and NELM=\<length>. Also adding a $ suffix to the _DBFSTRING type will also retrieve as char arrays. In pcaspy program, they are PVs configured as {"type": "char", "count": \<length>}.

E.g. this is a char array record in EPICS IOC,

record(waveform, "MTEST:COMMAND")
{
    field (FTVL, "CHAR")
    field (NELM, "128")
}

Here shows how -S switch treats it as a string.

$ cainfo MTEST:COMMAND
MTEST:COMMAND
...
    Native data type: DBF_CHAR
    Request type:     DBR_CHAR
    Element count:    128

$ caget MTEST:COMMAND
MTEST:COMMAND 128 100 97 116 101 116 105 109 101 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 ...

$ caget -S MTEST:COMMAND
MTEST:COMMAND datetime