Not able to set bit wise on port FIRSTPORTB/C/CH with ul.d_bit_out()
Closed this issue · 3 comments
I have a USB-DIO24/37 and tried out the example code mcculw/examples/console/digital_out.py. It works fine and values are set on pins of FIRSTPORTA. The example code automatically chooses FIRSTPORTA. If I now choose FIRSTPORTB or C (or CH) and try to set a specific bit with the function ul.d_bit_out()
, I get the following error:
Traceback (most recent call last):
File "e:/test_digitalIO_MCC/digital_out_test.py", line 169, in <module>
TTL_devices[0].on(8)
File "e:/test_digitalIO_MCC/digital_out_test.py", line 146, in on
return self.set(channel, 1)
File "e:/test_digitalIO_MCC/digital_out_test.py", line 132, in set
ul.d_bit_out(self.board_number, port_obj.type, bit_num, bit_value)
File "C:\Program Files\Python37\lib\site-packages\mcculw\ul.py", line 2546, in d_bit_out
_check_err(_cbw.cbDBitOut(board_num, port_type, bit_num, bit_value))
File "C:\Program Files\Python37\lib\site-packages\mcculw\ul.py", line 6128, in _check_err
raise ULError(errcode)
mcculw.ul.ULError: Error 11: Invalid digital port number.
Supprisingly, if I use the ul.d_out()
function to set the whole byte-array of a port, it works fine for all ports and I measured the pin-values and everything is fine. The ul.d_bit_out()
function would be far more convinient though...
when using the d_bit_in() or d_bit_out() functions, you MUST always use FIRSTPORTA. Set the bit_num parameter to a value between 0 and 23.
You do need to use the correct port name to configure the port using d_config_port() such as:
d_config_port(board_num, DigitalPortType.FIRSTPORTA, DigitalIODirection.Out)
d_config_port(board_num, DigitalPortType.FIRSTPORTB, DigitalIODirection.Out)
d_config_port(board_num, DigitalPortType.FIRSTPORTCL, DigitalIODirection.Out)
d_config_port(board_num, DigitalPortType.FIRSTPORTCH, DigitalIODirection.Out)
When you want to write out to any of the DIO of your USB-DIO24, you would use:
d_bit_out(board_num, DigitalPortType.FIRSTPORTA, bit_num, bit_value)
where:
bit_num is an integer between 0 and 23,
bit_value = 0 (off) or 1 (on).
Yes, d_out() works as you stated above.
Notes:
- if you want to have a combination of digital inputs and outputs, you still can, just configure the port as needed using d_config_port() with the correct DigitalPortType of FIRSTPORTA/B/CL/CH for input or output. Then when you want to read or write to a bit, you use an integer between 0 and 23 with d_bit_in() or d_bit_out().
- For users of other MCC devices having an AUXPORT instead of FIRSTPORTA/B/... the same is true, but you will need to use the AUXPORT (these are normally bit configurable.
- if you have a device such as USB-DIO96 series, the same is true for d_bit_in/out() where you exclusively use FIRSTPORTA, but there are many port DigitalPortTypes, and so many more options for bit numbers (0 to 95)
- For more information on this please see https://www.mccdaq.com/pdfs/manuals/Mcculw_WebHelp/ULStart.htm
- select Contents Tab,
- Hardware Reference
- Digital Input/Output Hardware (see the table shown here)
- USB-1024 Series and USB-DIO24 Series
Thank you for your fast and helpfull response. I modified the test script to try that, see attachment.
"""
File: digital_out.py
Library Call Demonstrated: mcculw.ul.d_out() and mcculw.d_bit_out()
Purpose: Writes to a digital output port.
Demonstration: Configures the first digital port for output
(if necessary) and writes a value to the port and
the first bit.
Other Library Calls: mcculw.ul.d_config_port()
mcculw.ul.release_daq_device()
Special Requirements: Device must have a digital output port
or have digital ports programmable as output.
"""
from __future__ import absolute_import, division, print_function
from builtins import * # @UnusedWildImport
from mcculw import ul
from mcculw.enums import DigitalIODirection
from mcculw.device_info import DaqDeviceInfo
try:
from console_examples_util import config_first_detected_device
except ImportError:
from .console_examples_util import config_first_detected_device
def run_example():
# By default, the example detects and displays all available devices and
# selects the first device listed. Use the dev_id_list variable to filter
# detected devices by device ID (see UL documentation for dev ice IDs).
# If use_device_detection is set to False, the board_num variable needs to
# match the desired board number configured with Instacal.
use_device_detection = True
dev_id_list = []
board_num = 0
try:
if use_device_detection:
config_first_detected_device(board_num, dev_id_list)
daq_dev_info = DaqDeviceInfo(board_num)
if not daq_dev_info.supports_digital_io:
raise Exception('Error: The DAQ device does not support '
'digital I/O')
print('\nActive DAQ device: ', daq_dev_info.product_name, ' (',
daq_dev_info.unique_id, ')\n', sep='')
dio_info = daq_dev_info.get_dio_info()
# get all ports
ports = [port for port in dio_info.port_info if port.supports_output]
# If the port is configurable, configure it for output.
for port in ports:
if port.is_port_configurable:
ul.d_config_port(board_num, port.type, DigitalIODirection.OUT)
port = ports[0] # get FIRSTPORTA
# set it to all 0 via byte set
port_value = 0b00000000
print('Setting', port.type.name, 'to', port_value)
# Output the value to the port
ul.d_out(board_num, port.type, port_value)
# set it to all 0 via bit set
for i in range(24):
bit_num = i
bit_value = 0
print('Setting', port.type.name, 'bit', bit_num, 'to', bit_value)
# Output the value to the bit
ul.d_bit_out(board_num, port.type, bit_num, bit_value)
# set every second pin to high
for i in range(0, 24, 2):
bit_num = i
bit_value = 1
print('Setting', port.type.name, 'bit', bit_num, 'to', bit_value)
# Output the value to the bit
ul.d_bit_out(board_num, port.type, bit_num, bit_value)
except Exception as e:
print('\n', e)
finally:
if use_device_detection:
ul.release_daq_device(board_num)
if __name__ == '__main__':
run_example()
The code runs without error, this results in every second pin on LOW and the other ones on HIGH. EXCEPT: The first 4 bits of FIRSTPORTA are all HIGH.
Nevermind my last message, all works fine :)
Thank you!