Skip to content

Commit

Permalink
Dev updates for the Zebra IOC
Browse files Browse the repository at this point in the history
  • Loading branch information
mrakitin committed May 14, 2024
1 parent 9abfa20 commit af0f986
Show file tree
Hide file tree
Showing 4 changed files with 133 additions and 5 deletions.
5 changes: 3 additions & 2 deletions scripts/run-caproto-ioc.sh
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,8 @@
set -vxeuo pipefail

CAPROTO_IOC="${1:-srx_caproto_iocs.base}"

DEFAULT_PREFIX="BASE:{{Dev:Save1}}:"
CAPROTO_IOC_PREFIX="${2:-${DEFAULT_PREFIX}}"
# shellcheck source=/dev/null
if [ -f "/etc/profile.d/epics.sh" ]; then
. /etc/profile.d/epics.sh
Expand All @@ -12,4 +13,4 @@ fi
export EPICS_CAS_AUTO_BEACON_ADDR_LIST="no"
export EPICS_CAS_BEACON_ADDR_LIST="${EPICS_CA_ADDR_LIST:-127.0.0.255}"

python -m "${CAPROTO_IOC}" --prefix="BASE:{{Dev:Save1}}:" --list-pvs
python -m "${CAPROTO_IOC}" --prefix="${CAPROTO_IOC_PREFIX}" --list-pvs
7 changes: 7 additions & 0 deletions scripts/run-caproto-zebra-ioc.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
#!/bin/bash

set -vxeuo pipefail

SCRIPT_DIR="$(dirname "$0")"

bash "${SCRIPT_DIR}/run-caproto-ioc.sh" srx_caproto_iocs.zebra.caproto_ioc "XF:05IDD-ES:1{{Dev:Zebra2}}:"
7 changes: 5 additions & 2 deletions src/srx_caproto_iocs/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -104,8 +104,7 @@ async def queue(self, instance, async_lib):
)
thread.start()

@stage.putter
async def stage(self, instance, value):
async def _stage(self, instance, value):
"""The stage method to perform preparation of a dataset to save the data."""
if (
instance.value in [True, StageStates.STAGED.value]
Expand Down Expand Up @@ -150,6 +149,10 @@ async def stage(self, instance, value):

return False

@stage.putter
async def stage(self, *args, **kwargs):
return await self._stage(*args, **kwargs)

def _get_current_dataset(self, frame):
"""The method to return a desired dataset.
Expand Down
119 changes: 118 additions & 1 deletion src/srx_caproto_iocs/zebra/caproto_ioc.py
Original file line number Diff line number Diff line change
@@ -1,20 +1,137 @@
from __future__ import annotations

import textwrap
from pprint import pformat

from caproto.asyncio.client import Context
from caproto.server import run, template_arg_parser

from ..base import CaprotoSaveIOC, check_args
from ..utils import now

# def export_nano_zebra_data(zebra, filepath, fastaxis):
# j = 0
# while zebra.pc.data_in_progress.get() == 1:
# print("Waiting for zebra...")
# ttime.sleep(0.1)
# j += 1
# if j > 10:
# print("THE ZEBRA IS BEHAVING BADLY CARRYING ON")
# break

# time_d = zebra.pc.data.time.get()
# enc1_d = zebra.pc.data.enc1.get()
# enc2_d = zebra.pc.data.enc2.get()
# enc3_d = zebra.pc.data.enc3.get()

# px = zebra.pc.pulse_step.get()
# if fastaxis == 'NANOHOR':
# # Add half pixelsize to correct encoder
# enc1_d = enc1_d + (px / 2)
# elif fastaxis == 'NANOVER':
# # Add half pixelsize to correct encoder
# enc2_d = enc2_d + (px / 2)
# elif fastaxis == 'NANOZ':
# # Add half pixelsize to correct encoder
# enc3_d = enc3_d + (px / 2)

# size = (len(time_d),)
# with h5py.File(filepath, "w") as f:
# dset0 = f.create_dataset("zebra_time", size, dtype="f")
# dset0[...] = np.array(time_d)
# dset1 = f.create_dataset("enc1", size, dtype="f")
# dset1[...] = np.array(enc1_d)
# dset2 = f.create_dataset("enc2", size, dtype="f")
# dset2[...] = np.array(enc2_d)
# dset3 = f.create_dataset("enc3", size, dtype="f")
# dset3[...] = np.array(enc3_d)


# class ZebraPositionCaptureData(Device):
# """
# Data arrays for the Zebra position capture function and their metadata.
# """
# # Data arrays
# ...
# enc1 = Cpt(EpicsSignal, "PC_ENC1") # XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC1
# enc2 = Cpt(EpicsSignal, "PC_ENC2") # XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC2
# enc3 = Cpt(EpicsSignal, "PC_ENC3") # XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC3
# time = Cpt(EpicsSignal, "PC_TIME") # XF:05IDD-ES:1{Dev:Zebra2}:PC_TIME
# ...

# class ZebraPositionCapture(Device):
# """
# Signals for the position capture function of the Zebra
# """

# # Configuration settings and status PVs
# ...
# pulse_step = Cpt(EpicsSignalWithRBV, "PC_PULSE_STEP") # XF:05IDD-ES:1{Dev:Zebra2}:PC_PULSE_STEP
# ...
# data_in_progress = Cpt(EpicsSignalRO, "ARRAY_ACQ") # XF:05IDD-ES:1{Dev:Zebra2}:ARRAY_ACQ
# ...
# data = Cpt(ZebraPositionCaptureData, "")

# nanoZebra = SRXZebra(
# "XF:05IDD-ES:1{Dev:Zebra2}:", name="nanoZebra",
# read_attrs=["pc.data.enc1", "pc.data.enc2", "pc.data.enc3", "pc.data.time"],
# )


class ZebraSaveIOC(CaprotoSaveIOC):
"""Zebra caproto save IOC."""

# enc1 = Cpt(EpicsSignal, "PC_ENC1")
# enc2 = Cpt(EpicsSignal, "PC_ENC2")
# enc3 = Cpt(EpicsSignal, "PC_ENC3")
# enc4 = Cpt(EpicsSignal, "PC_ENC4")

# data_in_progress = pvproperty() # +
# time_d = pvproperty()
# enc1_d = pvproperty()
# enc2_d = pvproperty()
# enc3_d = pvproperty()
# pulse_step = pvproperty()

def __init__(self, *args, external_pvs=None, **kwargs):
"""Init method.
external_pvs : dict
a dictionary of external PVs with keys as human-readable names.
"""
super().__init__(*args, **kwargs)
self._external_pvs = external_pvs

async def _stage(self, *args, **kwargs):
await super()._stage(*args, **kwargs)
client_context = Context()
res = {}
if self._external_pvs is not None:
pvobjects = await client_context.get_pvs(*self._external_pvs.values())
for i, (name, pv) in enumerate(self._external_pvs.items()): # noqa: B007
pvobject = pvobjects[i]
# print(f"{now()}: {pvobject = }")
ret = await pvobject.read()
# print(f"{now()}: {val.data}")
res[name] = {"data": ret.data, "shape": ret.data.shape}
print(f"{now()}:\n{pformat(res)}")
return True


if __name__ == "__main__":
parser, split_args = template_arg_parser(
default_prefix="", desc=textwrap.dedent(ZebraSaveIOC.__doc__)
)
ioc_options, run_options = check_args(parser, split_args)
ioc = ZebraSaveIOC(**ioc_options) # TODO: pass libca IOC PVs of interest

external_pvs = {
"pulse_step": "XF:05IDD-ES:1{Dev:Zebra2}:PC_PULSE_STEP",
"data_in_progress": "XF:05IDD-ES:1{Dev:Zebra2}:ARRAY_ACQ",
"enc1": "XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC1",
"enc2": "XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC2",
"enc3": "XF:05IDD-ES:1{Dev:Zebra2}:PC_ENC3",
"time": "XF:05IDD-ES:1{Dev:Zebra2}:PC_TIME",
}

ioc = ZebraSaveIOC(external_pvs=external_pvs, **ioc_options)
run(ioc.pvdb, **run_options)

0 comments on commit af0f986

Please sign in to comment.