Memory layout of a data structure: Difference between revisions
Content added Content deleted
(→{{header|J}}: define helpers, show an example) |
Thundergnat (talk | contribs) m (syntax highlighting fixup automation) |
||
Line 36: | Line 36: | ||
25 - |
25 - |
||
=={{header|6502 Assembly}}== |
=={{header|6502 Assembly}}== |
||
< |
<syntaxhighlight lang="6502asm">soft_rs232_lo equ $20 ;%87654321 |
||
soft_rs232_hi equ $21 ;%-------9</ |
soft_rs232_hi equ $21 ;%-------9</syntaxhighlight> |
||
The values $20 and $21 do not matter; any zero page memory location is acceptable. The comments explain which bit position represents which pin, written in the format one would write a binary literal in the assembler. A "-" means that particular bit is unused. |
The values $20 and $21 do not matter; any zero page memory location is acceptable. The comments explain which bit position represents which pin, written in the format one would write a binary literal in the assembler. A "-" means that particular bit is unused. |
||
This example non-destructively writes a "1" to pin 3: |
This example non-destructively writes a "1" to pin 3: |
||
< |
<syntaxhighlight lang="6502asm">LDA soft_rs232_lo |
||
ora #%00000100 |
ora #%00000100 |
||
sta soft_rs232_lo</ |
sta soft_rs232_lo</syntaxhighlight> |
||
The common practice is to have "soft" ports in zero page which get written to the memory-mapped location of the actual hardware interface by only a single subroutine that is run at a fixed interval. All other routines only ever update the "soft" port. (Hardware ports such as this example are typically write-only so the only way to non-destructively write to individual bits is through this indirect method.) |
The common practice is to have "soft" ports in zero page which get written to the memory-mapped location of the actual hardware interface by only a single subroutine that is run at a fixed interval. All other routines only ever update the "soft" port. (Hardware ports such as this example are typically write-only so the only way to non-destructively write to individual bits is through this indirect method.) |
||
Line 50: | Line 50: | ||
Thanks to the low-level nature of assembly, this task is actually rather straightforward. Using <code>equ</code> directives we can easily abstract the bit numbers with convenient labels without having to remember what they are. |
Thanks to the low-level nature of assembly, this task is actually rather straightforward. Using <code>equ</code> directives we can easily abstract the bit numbers with convenient labels without having to remember what they are. |
||
< |
<syntaxhighlight lang="68000devpac">BIT_0 equ $1 |
||
BIT_1 equ $2 |
BIT_1 equ $2 |
||
BIT_2 equ $4 |
BIT_2 equ $4 |
||
Line 68: | Line 68: | ||
RS232_9_DSR equ BIT_6 |
RS232_9_DSR equ BIT_6 |
||
RS232_9_SG equ BIT_5 |
RS232_9_SG equ BIT_5 |
||
RS232_9_CD equ BIT_1</ |
RS232_9_CD equ BIT_1</syntaxhighlight> |
||
With these aliases defined, we can easily write these constants, or any combination thereof, to the memory-mapped RS232 port. |
With these aliases defined, we can easily write these constants, or any combination thereof, to the memory-mapped RS232 port. |
||
Line 74: | Line 74: | ||
(Disclaimer: I have no idea how this protocol actually works. So there's a good chance that these values should '''not''' be combined this way when working with actual RS232 hardware. But that's not really important to this task. I'm just showing how you can define constants and write them to the port.) |
(Disclaimer: I have no idea how this protocol actually works. So there's a good chance that these values should '''not''' be combined this way when working with actual RS232 hardware. But that's not really important to this task. I'm just showing how you can define constants and write them to the port.) |
||
< |
<syntaxhighlight lang="68000devpac">rs232_9pin_port equ $A00000 |
||
;I chose $A00000 arbitrarily as an example, its actual address depends on the wiring. |
;I chose $A00000 arbitrarily as an example, its actual address depends on the wiring. |
||
MOVE.W #RS232_9_CTS,rs232_9pin_port |
MOVE.W #RS232_9_CTS,rs232_9pin_port |
||
MOVE.W #RS232_9_CTS|RS232_9_RD|RS232_9_SG,rs232_9pin_port ;bitwise OR can be used at compile time to combine the labels.</ |
MOVE.W #RS232_9_CTS|RS232_9_RD|RS232_9_SG,rs232_9pin_port ;bitwise OR can be used at compile time to combine the labels.</syntaxhighlight> |
||
=={{header|Ada}}== |
=={{header|Ada}}== |
||
< |
<syntaxhighlight lang="ada">type Bit is mod 2; |
||
type Rs_232_Layout is record |
type Rs_232_Layout is record |
||
Carrier_Detect : Bit; |
Carrier_Detect : Bit; |
||
Line 105: | Line 105: | ||
Clear_To_Send at 0 range 7..7; |
Clear_To_Send at 0 range 7..7; |
||
Ring_Indicator at 0 range 8..8; |
Ring_Indicator at 0 range 8..8; |
||
end record;</ |
end record;</syntaxhighlight> |
||
=={{header|ALGOL 68}}== |
=={{header|ALGOL 68}}== |
||
Line 112: | Line 112: | ||
{{works with|ALGOL 68G|Any - tested with release [http://sourceforge.net/projects/algol68/files/algol68g/algol68g-1.18.0/algol68g-1.18.0-9h.tiny.el5.centos.fc11.i386.rpm/download 1.18.0-9h.tiny]}} |
{{works with|ALGOL 68G|Any - tested with release [http://sourceforge.net/projects/algol68/files/algol68g/algol68g-1.18.0/algol68g-1.18.0-9h.tiny.el5.centos.fc11.i386.rpm/download 1.18.0-9h.tiny]}} |
||
{{works with|ELLA ALGOL 68|Any (with appropriate job cards) - tested with release [http://sourceforge.net/projects/algol68/files/algol68toc/algol68toc-1.8.8d/algol68toc-1.8-8d.fc9.i386.rpm/download 1.8-8d]}} |
{{works with|ELLA ALGOL 68|Any (with appropriate job cards) - tested with release [http://sourceforge.net/projects/algol68/files/algol68toc/algol68toc-1.8.8d/algol68toc-1.8-8d.fc9.i386.rpm/download 1.8-8d]}} |
||
< |
<syntaxhighlight lang="algol68">MODE RSTWOTHREETWO = BITS; |
||
INT ofs = bits width - 9; |
INT ofs = bits width - 9; |
||
INT |
INT |
||
Line 131: | Line 131: | ||
rs232 bits := bits pack((FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE)); |
rs232 bits := bits pack((FALSE, TRUE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE)); |
||
print(("received data: ",received data ELEM rs232bits, new line))</ |
print(("received data: ",received data ELEM rs232bits, new line))</syntaxhighlight> |
||
Output: |
Output: |
||
<pre> |
<pre> |
||
Line 140: | Line 140: | ||
=={{header|C}}/{{header|C++}}== |
=={{header|C}}/{{header|C++}}== |
||
Note: The order of the fields is implementation-defined (i.e. the first bit might be the least-significant one or the most-significant one). On GCC and MSVC++, the first bit is the least-significant one. |
Note: The order of the fields is implementation-defined (i.e. the first bit might be the least-significant one or the most-significant one). On GCC and MSVC++, the first bit is the least-significant one. |
||
< |
<syntaxhighlight lang="c">struct RS232_data |
||
{ |
{ |
||
unsigned carrier_detect : 1; |
unsigned carrier_detect : 1; |
||
Line 151: | Line 151: | ||
unsigned clear_to_send : 1; |
unsigned clear_to_send : 1; |
||
unsigned ring_indicator : 1; |
unsigned ring_indicator : 1; |
||
};</ |
};</syntaxhighlight> |
||
The ":1" gives the number of allocated bits. For unused bits (e.g. pin 11 in the 25-pin version above) the field name can be omitted. |
The ":1" gives the number of allocated bits. For unused bits (e.g. pin 11 in the 25-pin version above) the field name can be omitted. |
||
Line 160: | Line 160: | ||
Implementation uses tango's BitArray structure. |
Implementation uses tango's BitArray structure. |
||
{{libheader|tango}} |
{{libheader|tango}} |
||
< |
<syntaxhighlight lang="d">module controlFieldsInStruct; |
||
import tango.core.BitArray; |
import tango.core.BitArray; |
||
Line 230: | Line 230: | ||
return 0; |
return 0; |
||
}</ |
}</syntaxhighlight> |
||
Output: |
Output: |
||
Line 238: | Line 238: | ||
===Phobos version=== |
===Phobos version=== |
||
Not tested. |
Not tested. |
||
< |
<syntaxhighlight lang="d">import std.bitmanip; |
||
struct RS232_data { |
struct RS232_data { |
||
Line 268: | Line 268: | ||
} |
} |
||
void main() {}</ |
void main() {}</syntaxhighlight> |
||
=={{header|Forth}}== |
=={{header|Forth}}== |
||
Low level hardware control is a typical use of Forth. None of this is standard, however, since hardware I/O mechanisms differ on different systems. Forth does not have a structure mechanism, much less bitfields. These would be represented instead via bitmask constants if doing real serial port control. |
Low level hardware control is a typical use of Forth. None of this is standard, however, since hardware I/O mechanisms differ on different systems. Forth does not have a structure mechanism, much less bitfields. These would be represented instead via bitmask constants if doing real serial port control. |
||
< |
<syntaxhighlight lang="forth"> : masks ( n -- ) 0 do 1 i lshift constant loop ; |
||
9 masks DCD RxD TxD DTR SG DSR RTS CTS RI</ |
9 masks DCD RxD TxD DTR SG DSR RTS CTS RI</syntaxhighlight> |
||
Example usage, assuming I/O primitives '''in''' and '''out''': |
Example usage, assuming I/O primitives '''in''' and '''out''': |
||
< |
<syntaxhighlight lang="forth"> hex |
||
3fd constant com1-ctrl |
3fd constant com1-ctrl |
||
decimal |
decimal |
||
Line 302: | Line 302: | ||
wait-rx |
wait-rx |
||
2/ |
2/ |
||
loop drop ;</ |
loop drop ;</syntaxhighlight> |
||
Of course, this is a very simplified view of the full RS-232 protocol. Also, although this represents the order of the pins in a D-9 connector, this would not necessarily be the same as the order of the bits in a control register. |
Of course, this is a very simplified view of the full RS-232 protocol. Also, although this represents the order of the pins in a D-9 connector, this would not necessarily be the same as the order of the bits in a control register. |
||
Line 308: | Line 308: | ||
=={{header|Fortran}}== |
=={{header|Fortran}}== |
||
===Modern=== |
===Modern=== |
||
F90 introduced the ability to define compound data aggregates, as had been used from the start by COBOL in the 1960s. Thus, one could define < |
F90 introduced the ability to define compound data aggregates, as had been used from the start by COBOL in the 1960s. Thus, one could define <syntaxhighlight lang="fortran"> TYPE RS232PIN9 |
||
LOGICAL CARRIER_DETECT !1 |
LOGICAL CARRIER_DETECT !1 |
||
LOGICAL RECEIVED_DATA !2 |
LOGICAL RECEIVED_DATA !2 |
||
Line 318: | Line 318: | ||
LOGICAL CLEAR_TO_SEND !8 |
LOGICAL CLEAR_TO_SEND !8 |
||
LOGICAL RING_INDICATOR !9 |
LOGICAL RING_INDICATOR !9 |
||
END TYPE RS232PIN9 </ |
END TYPE RS232PIN9 </syntaxhighlight> |
||
But it would be nearly pointless to do so. |
But it would be nearly pointless to do so. |
||
Line 342: | Line 342: | ||
=={{header|Free Pascal}}== |
=={{header|Free Pascal}}== |
||
The FPC (Free Pascal compiler) carefully defines the internal memory structure of data type in its “Programmer’s guide”. |
The FPC (Free Pascal compiler) carefully defines the internal memory structure of data type in its “Programmer’s guide”. |
||
< |
<syntaxhighlight lang="pascal">program rs232(input, output, stdErr); |
||
type |
type |
||
{$packEnum 2}{$scopedEnums off} |
{$packEnum 2}{$scopedEnums off} |
||
Line 364: | Line 364: | ||
writeLn(binStr(signalMemoryStructure, bitSizeOf(signal))); |
writeLn(binStr(signalMemoryStructure, bitSizeOf(signal))); |
||
end; |
end; |
||
end.</ |
end.</syntaxhighlight> |
||
{{Out}} |
{{Out}} |
||
<pre>0000000000010000</pre> |
<pre>0000000000010000</pre> |
||
=={{header|FreeBASIC}}== |
=={{header|FreeBASIC}}== |
||
< |
<syntaxhighlight lang="freebasic">' FB 1.05.0 Win64 |
||
' using bit fields |
' using bit fields |
||
Line 385: | Line 385: | ||
Print SizeOf(RS232_Pin9) '' 2 bytes |
Print SizeOf(RS232_Pin9) '' 2 bytes |
||
Sleep</ |
Sleep</syntaxhighlight> |
||
=={{header|Go}}== |
=={{header|Go}}== |
||
Go does not have named bits as part of the type system. Instead, constants are typically defined as shown. For a word of bits with special meanings like this, a type would be defined though, as shown. Static typing rules then control assignments and comparisons at the word level. At the bit level, it helps to follow naming conventions so that, say, using a 9-pin constant on a 25-pin word would be an obvious error in the source code. |
Go does not have named bits as part of the type system. Instead, constants are typically defined as shown. For a word of bits with special meanings like this, a type would be defined though, as shown. Static typing rules then control assignments and comparisons at the word level. At the bit level, it helps to follow naming conventions so that, say, using a 9-pin constant on a 25-pin word would be an obvious error in the source code. |
||
< |
<syntaxhighlight lang="go">package main |
||
import "fmt" |
import "fmt" |
||
Line 411: | Line 411: | ||
p := RI9 | TD9 | CD9 |
p := RI9 | TD9 | CD9 |
||
fmt.Printf("Type=%T value=%#04x\n", p, p) |
fmt.Printf("Type=%T value=%#04x\n", p, p) |
||
}</ |
}</syntaxhighlight> |
||
{{out}} |
{{out}} |
||
<pre> |
<pre> |
||
Line 419: | Line 419: | ||
=={{header|J}}== |
=={{header|J}}== |
||
J does not support "structures", nor "fields in a structure". Instead, J supports arrays. And, of course, J could have labels corresponding to the elements of an array representing the state (voltage, current, logical bit value, whatever) of each pin of a 9-pin RS-232 plug: |
J does not support "structures", nor "fields in a structure". Instead, J supports arrays. And, of course, J could have labels corresponding to the elements of an array representing the state (voltage, current, logical bit value, whatever) of each pin of a 9-pin RS-232 plug: |
||
< |
<syntaxhighlight lang="j">default=: 0#~#|:'labels comments'=:|:(4 ({.@;:@{. ; }.)]);._2 {{)n |
||
RD Received data |
RD Received data |
||
TD Transmitted data |
TD Transmitted data |
||
Line 432: | Line 432: | ||
indices=: labels (i. ;: ::]) ] |
indices=: labels (i. ;: ::]) ] |
||
ndx=: [ {~ [ indices ] |
ndx=: [ {~ [ indices ] |
||
asgn=: {{ y (x indices m)} x }}</ |
asgn=: {{ y (x indices m)} x }}</syntaxhighlight> |
||
Example use: |
Example use: |
||
< |
<syntaxhighlight lang="j"> example=: default NB. new instance |
||
example ndx 'RI CTS' |
example ndx 'RI CTS' |
||
0 0 |
0 0 |
||
example=: example 'RI RTS TD' asgn 1 2 3 |
example=: example 'RI RTS TD' asgn 1 2 3 |
||
example ndx 'RI CTS' |
example ndx 'RI CTS' |
||
1 0</ |
1 0</syntaxhighlight> |
||
=={{header|Julia}}== |
=={{header|Julia}}== |
||
Line 459: | Line 459: | ||
</pre> |
</pre> |
||
We can then make the following code for a new serial port type: |
We can then make the following code for a new serial port type: |
||
<syntaxhighlight lang="julia"> |
|||
<lang Julia> |
|||
mutable struct NinePinSerialPort |
mutable struct NinePinSerialPort |
||
pins::BitArray |
pins::BitArray |
||
Line 483: | Line 483: | ||
println("CTS pin of port, which is pin $CTS, is now $(port[CTS])") |
println("CTS pin of port, which is pin $CTS, is now $(port[CTS])") |
||
println("port is now: $port") |
println("port is now: $port") |
||
</syntaxhighlight> |
|||
</lang> |
|||
{{output}} |
{{output}} |
||
<pre> |
<pre> |
||
Line 496: | Line 496: | ||
However, if access by both position and name is required, then a data class with 9 named boolean properties would be more suitable. This automatically generates functions called component1, component2 etc. to get the pin values by pin number. However, a function needs to be written manually to set pin values by pin number: |
However, if access by both position and name is required, then a data class with 9 named boolean properties would be more suitable. This automatically generates functions called component1, component2 etc. to get the pin values by pin number. However, a function needs to be written manually to set pin values by pin number: |
||
< |
<syntaxhighlight lang="scala">// version 1.0.6 |
||
const val OFF = false |
const val OFF = false |
||
Line 537: | Line 537: | ||
println(toOnOff(plug.dataTerminalReady)) // print value of pin 4 by name |
println(toOnOff(plug.dataTerminalReady)) // print value of pin 4 by name |
||
println(toOnOff(plug.ringIndicator)) // print value of pin 9 by name |
println(toOnOff(plug.ringIndicator)) // print value of pin 9 by name |
||
}</ |
}</syntaxhighlight> |
||
{{out}} |
{{out}} |
||
Line 550: | Line 550: | ||
Defining structs in MATLAB is kind of bulky, making a class definition might be cleaner for this purpose. If you need to enumerate each pin rather than set the state of the pin using the name of the pin, you can use struct2cell() on the rs232 struct, which will return a cell array whose entries are the value of each of the structs fields in the order in which they were defined. |
Defining structs in MATLAB is kind of bulky, making a class definition might be cleaner for this purpose. If you need to enumerate each pin rather than set the state of the pin using the name of the pin, you can use struct2cell() on the rs232 struct, which will return a cell array whose entries are the value of each of the structs fields in the order in which they were defined. |
||
< |
<syntaxhighlight lang="matlab">>> rs232 = struct('carrier_detect', logical(1),... |
||
'received_data' , logical(1), ... |
'received_data' , logical(1), ... |
||
'transmitted_data', logical(1),... |
'transmitted_data', logical(1),... |
||
Line 584: | Line 584: | ||
[1] |
[1] |
||
[1] |
[1] |
||
[1]</ |
[1]</syntaxhighlight> |
||
=={{header|Mercury}}== |
=={{header|Mercury}}== |
||
Line 594: | Line 594: | ||
=== rs232.m === |
=== rs232.m === |
||
<syntaxhighlight lang="mercury"> |
|||
<lang Mercury> |
|||
:- module rs232. |
:- module rs232. |
||
Line 665: | Line 665: | ||
:- end_module rs232. |
:- end_module rs232. |
||
</syntaxhighlight> |
|||
</lang> |
|||
=== rs232_main.m === |
=== rs232_main.m === |
||
< |
<syntaxhighlight lang="mercury">:- module rs232_main. |
||
:- interface. |
:- interface. |
||
Line 705: | Line 705: | ||
:- end_module rs232_main. |
:- end_module rs232_main. |
||
</syntaxhighlight> |
|||
</lang> |
|||
==== Usage and output ==== |
==== Usage and output ==== |
||
Line 716: | Line 716: | ||
=={{header|Nim}}== |
=={{header|Nim}}== |
||
< |
<syntaxhighlight lang="nim">type |
||
rs232Data = enum |
rs232Data = enum |
||
carrierDetect, |
carrierDetect, |
||
Line 734: | Line 734: | ||
let readValue: uint16 = 123 |
let readValue: uint16 = 123 |
||
bv = cast[set[rs232Data]](readValue) # Conversion of a read value to bitvector |
bv = cast[set[rs232Data]](readValue) # Conversion of a read value to bitvector |
||
echo bv</ |
echo bv</syntaxhighlight> |
||
Output: |
Output: |
||
<pre>273 |
<pre>273 |
||
Line 741: | Line 741: | ||
=={{header|OCaml}}== |
=={{header|OCaml}}== |
||
'''Library:''' [http://code.google.com/p/ocaml-extlib/ extlib] |
'''Library:''' [http://code.google.com/p/ocaml-extlib/ extlib] |
||
< |
<syntaxhighlight lang="ocaml">open ExtLib |
||
class rs232_data = object |
class rs232_data = object |
||
val d = BitSet.create 9 |
val d = BitSet.create 9 |
||
Line 765: | Line 765: | ||
method set_ring_indicator b = (if b then BitSet.set else BitSet.unset) d 8 |
method set_ring_indicator b = (if b then BitSet.set else BitSet.unset) d 8 |
||
end |
end |
||
;;</ |
;;</syntaxhighlight> |
||
=={{header|Pascal}}== |
=={{header|Pascal}}== |
||
Line 773: | Line 773: | ||
=={{header|Perl}}== |
=={{header|Perl}}== |
||
< |
<syntaxhighlight lang="perl">use Bit::Vector::Minimal qw(); |
||
my $vec = Bit::Vector::Minimal->new(size => 24); |
my $vec = Bit::Vector::Minimal->new(size => 24); |
||
Line 802: | Line 802: | ||
$vec->set($rs232{'RD Received data'}, 1); |
$vec->set($rs232{'RD Received data'}, 1); |
||
$vec->get($rs232{'TC Transmit clock'});</ |
$vec->get($rs232{'TC Transmit clock'});</syntaxhighlight> |
||
=={{header|Phix}}== |
=={{header|Phix}}== |
||
Phix does not support bit-fields directly. The nearest/sanest thing to do probably goes something like this (completely untested) |
Phix does not support bit-fields directly. The nearest/sanest thing to do probably goes something like this (completely untested) |
||
<!--< |
<!--<syntaxhighlight lang="phix">--> |
||
<span style="color: #008080;">constant</span> <span style="color: #000000;">CD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">RD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">2</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">TD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">3</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">DTR</span><span style="color: #0000FF;">=</span><span style="color: #000000;">4</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">...</span> |
<span style="color: #008080;">constant</span> <span style="color: #000000;">CD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">1</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">RD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">2</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">TD</span><span style="color: #0000FF;">=</span><span style="color: #000000;">3</span><span style="color: #0000FF;">,</span> <span style="color: #000000;">DTR</span><span style="color: #0000FF;">=</span><span style="color: #000000;">4</span><span style="color: #0000FF;">,</span> <span style="color: #0000FF;">...</span> |
||
<span style="color: #004080;">atom</span> <span style="color: #000000;">addr</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">allocate</span><span style="color: #0000FF;">(</span><span style="color: #000000;">2</span><span style="color: #0000FF;">)</span> <span style="color: #000080;font-style:italic;">-- or wherever |
<span style="color: #004080;">atom</span> <span style="color: #000000;">addr</span> <span style="color: #0000FF;">=</span> <span style="color: #7060A8;">allocate</span><span style="color: #0000FF;">(</span><span style="color: #000000;">2</span><span style="color: #0000FF;">)</span> <span style="color: #000080;font-style:italic;">-- or wherever |
||
Line 816: | Line 816: | ||
<span style="color: #000000;">bits</span><span style="color: #0000FF;">[</span><span style="color: #000000;">DTR</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">1</span> |
<span style="color: #000000;">bits</span><span style="color: #0000FF;">[</span><span style="color: #000000;">DTR</span><span style="color: #0000FF;">]</span> <span style="color: #0000FF;">=</span> <span style="color: #000000;">1</span> |
||
<span style="color: #7060A8;">poke2</span><span style="color: #0000FF;">(</span><span style="color: #000000;">addr</span><span style="color: #0000FF;">,</span><span style="color: #7060A8;">bits_to_int</span><span style="color: #0000FF;">(</span><span style="color: #000000;">bits</span><span style="color: #0000FF;">))</span> |
<span style="color: #7060A8;">poke2</span><span style="color: #0000FF;">(</span><span style="color: #000000;">addr</span><span style="color: #0000FF;">,</span><span style="color: #7060A8;">bits_to_int</span><span style="color: #0000FF;">(</span><span style="color: #000000;">bits</span><span style="color: #0000FF;">))</span> |
||
<!--</ |
<!--</syntaxhighlight>--> |
||
Naturally, you would be well advised to sequester such grubby details away in a small and separate unit/source code file (eg RS232.e) with a domain specific public API that does not leak implementation details (eg keep those constants private). There are 1/2/4/8 byte variants of peek and poke, and int-to-bits can extract anything from 1 to 53 bits on a 32-bit runtime, or up to 64 on a 64-bit runtime. |
Naturally, you would be well advised to sequester such grubby details away in a small and separate unit/source code file (eg RS232.e) with a domain specific public API that does not leak implementation details (eg keep those constants private). There are 1/2/4/8 byte variants of peek and poke, and int-to-bits can extract anything from 1 to 53 bits on a 32-bit runtime, or up to 64 on a 64-bit runtime. |
||
Line 827: | Line 827: | ||
'[http://software-lab.de/doc/refX.html#x| x|]', |
'[http://software-lab.de/doc/refX.html#x| x|]', |
||
or tested with '[http://software-lab.de/doc/refB.html#bit? bit?]'. |
or tested with '[http://software-lab.de/doc/refB.html#bit? bit?]'. |
||
< |
<syntaxhighlight lang="picolisp"># Define bit constants |
||
(for (N . Mask) '(CD RD TD DTR SG DSR RTS CTS RI) |
(for (N . Mask) '(CD RD TD DTR SG DSR RTS CTS RI) |
||
(def Mask (>> (- 1 N) 1)) ) |
(def Mask (>> (- 1 N) 1)) ) |
||
Line 833: | Line 833: | ||
# Test if Clear to send |
# Test if Clear to send |
||
(when (bit? CTS Data) |
(when (bit? CTS Data) |
||
... )</ |
... )</syntaxhighlight> |
||
=={{header|PL/I}}== |
=={{header|PL/I}}== |
||
<syntaxhighlight lang="pl/i"> |
|||
<lang PL/I> |
|||
declare 1 RS232_layout, |
declare 1 RS232_layout, |
||
2 Carrier_Detect Bit(1), |
2 Carrier_Detect Bit(1), |
||
Line 847: | Line 847: | ||
2 Clear_To_Send Bit(1), |
2 Clear_To_Send Bit(1), |
||
2 Ring_Indicator Bit(1); |
2 Ring_Indicator Bit(1); |
||
</syntaxhighlight> |
|||
</lang> |
|||
=={{header|Python}}== |
=={{header|Python}}== |
||
The ctypes module allows for the creation of Structures that can map between the structures of C and python datatypes. Within Structures, [http://docs.python.org/library/ctypes.html#bit-fields-in-structures-and-unions bit fields] can be created. |
The ctypes module allows for the creation of Structures that can map between the structures of C and python datatypes. Within Structures, [http://docs.python.org/library/ctypes.html#bit-fields-in-structures-and-unions bit fields] can be created. |
||
< |
<syntaxhighlight lang="python">from ctypes import Structure, c_int |
||
rs232_9pin = "_0 CD RD TD DTR SG DSR RTS CTS RI".split() |
rs232_9pin = "_0 CD RD TD DTR SG DSR RTS CTS RI".split() |
||
Line 864: | Line 864: | ||
class RS232_25pin(Structure): |
class RS232_25pin(Structure): |
||
_fields_ = [(__, c_int, 1) for __ in rs232_25pin]</ |
_fields_ = [(__, c_int, 1) for __ in rs232_25pin]</syntaxhighlight> |
||
=={{header|Racket}}== |
=={{header|Racket}}== |
||
< |
<syntaxhighlight lang="racket"> |
||
#lang racket |
#lang racket |
||
Line 883: | Line 883: | ||
((ctype-scheme->c _rs232) '(SG TD RI)) ; -> 276 |
((ctype-scheme->c _rs232) '(SG TD RI)) ; -> 276 |
||
((ctype-c->scheme _rs232) 276) ; -> '(TD SG RI) |
((ctype-c->scheme _rs232) 276) ; -> '(TD SG RI) |
||
</syntaxhighlight> |
|||
</lang> |
|||
=={{header|Raku}}== |
=={{header|Raku}}== |
||
(formerly Perl 6) |
(formerly Perl 6) |
||
The following is specced to work, but implementation of shaped arrays is not quite complete. |
The following is specced to work, but implementation of shaped arrays is not quite complete. |
||
<lang |
<syntaxhighlight lang="raku" line>enum T_RS232 < |
||
carrier_detect |
carrier_detect |
||
received_data |
received_data |
||
Line 902: | Line 902: | ||
my bit @signal[T_RS232]; |
my bit @signal[T_RS232]; |
||
@signal[signal_ground] = 1;</ |
@signal[signal_ground] = 1;</syntaxhighlight> |
||
In the absence of shaped arrays, you can do the usual bit-twiddling tricks on a native integer of sufficient size. (Such an integer could presumably be mapped directly to a device register.) |
In the absence of shaped arrays, you can do the usual bit-twiddling tricks on a native integer of sufficient size. (Such an integer could presumably be mapped directly to a device register.) |
||
<lang |
<syntaxhighlight lang="raku" line>$signal +|= 1 +< signal_ground;</syntaxhighlight> |
||
Using a native int is likelier to work on a big-endian machine in any case. Another almost-there solution is the mapping of C representational types into Raku for native interfaces, but it does not yet support bit fields. |
Using a native int is likelier to work on a big-endian machine in any case. Another almost-there solution is the mapping of C representational types into Raku for native interfaces, but it does not yet support bit fields. |
||
=={{header|REXX}}== |
=={{header|REXX}}== |
||
===version 1=== |
===version 1=== |
||
< |
<syntaxhighlight lang="rexx">/* REXX *************************************************************** |
||
* Decode Memory structure of RS-232 Plug Definition |
* Decode Memory structure of RS-232 Plug Definition |
||
* Not sure if I understood it completely :-) Open for corrections |
* Not sure if I understood it completely :-) Open for corrections |
||
Line 1,028: | Line 1,028: | ||
res=res||bs |
res=res||bs |
||
End |
End |
||
Return res</ |
Return res</syntaxhighlight> |
||
Output EBCDIC: |
Output EBCDIC: |
||
<pre> |
<pre> |
||
Line 1,071: | Line 1,071: | ||
===version 2=== |
===version 2=== |
||
Checks could be added to verify the number of pins selected, and also verify if the data (pin readings) specified is valid. |
Checks could be added to verify the number of pins selected, and also verify if the data (pin readings) specified is valid. |
||
< |
<syntaxhighlight lang="rexx">/*REXX program displays which pins are active of a 9 or 24 pin RS-232 plug. */ |
||
call rs_232 24, 127 /*the value for an RS-232 24 pin plug.*/ |
call rs_232 24, 127 /*the value for an RS-232 24 pin plug.*/ |
||
call rs_232 24, '020304x' /* " " " " " " " " */ |
call rs_232 24, '020304x' /* " " " " " " " " */ |
||
Line 1,114: | Line 1,114: | ||
say right(j, 5) 'pin is "on": ' @.pins.j |
say right(j, 5) 'pin is "on": ' @.pins.j |
||
end /*j*/ |
end /*j*/ |
||
return</ |
return</syntaxhighlight> |
||
'''output''' when using the default (internal) inputs: |
'''output''' when using the default (internal) inputs: |
||
<pre> |
<pre> |
||
Line 1,142: | Line 1,142: | ||
=={{header|Ruby}}== |
=={{header|Ruby}}== |
||
Uses the [http://redshift.sourceforge.net/bit-struct/ BitStruct] module, which is handy but awkward to instantiate objects. |
Uses the [http://redshift.sourceforge.net/bit-struct/ BitStruct] module, which is handy but awkward to instantiate objects. |
||
< |
<syntaxhighlight lang="ruby">require 'bit-struct' |
||
class RS232_9 < BitStruct |
class RS232_9 < BitStruct |
||
Line 1,171: | Line 1,171: | ||
puts sample2.inspect_detailed |
puts sample2.inspect_detailed |
||
puts "CD is #{sample2.cd == 1 ? 'on' : 'off'}"</ |
puts "CD is #{sample2.cd == 1 ? 'on' : 'off'}"</syntaxhighlight> |
||
<pre>num = 37 |
<pre>num = 37 |
||
Line 1,197: | Line 1,197: | ||
=={{header|Scala}}== |
=={{header|Scala}}== |
||
< |
<syntaxhighlight lang="scala">object Rs232Pins9 extends App { |
||
val (off: Boolean, on: Boolean) = (false, true) |
val (off: Boolean, on: Boolean) = (false, true) |
||
Line 1,236: | Line 1,236: | ||
println(toOnOff(plug.dataTerminalReady)) // print value of pin 4 by name |
println(toOnOff(plug.dataTerminalReady)) // print value of pin 4 by name |
||
println(toOnOff(plug.ringIndicator)) // print value of pin 9 by name |
println(toOnOff(plug.ringIndicator)) // print value of pin 9 by name |
||
}</ |
}</syntaxhighlight> |
||
=={{header|Tcl}}== |
=={{header|Tcl}}== |
||
This Tcl implementation represents the fields as bits in an integer. It provides two functions to get from symbolic pin names to the integer, and vice versa. |
This Tcl implementation represents the fields as bits in an integer. It provides two functions to get from symbolic pin names to the integer, and vice versa. |
||
< |
<syntaxhighlight lang="tcl">set rs232_bits {CD RD TD DTR SG DSR RTS CTS RI} |
||
proc rs232_encode args { |
proc rs232_encode args { |
||
Line 1,268: | Line 1,268: | ||
catch $test res |
catch $test res |
||
if {$res ne $expected} {puts "$test -> $res, expected $expected"} |
if {$res ne $expected} {puts "$test -> $res, expected $expected"} |
||
}</ |
}</syntaxhighlight> |
||
=={{header|Wren}}== |
=={{header|Wren}}== |
||
Line 1,278: | Line 1,278: | ||
As far as this task is concerned, below is a possible implementation for a 9-pin RS-232 plug which allows access by pin name or number and provides a comprehensive print out of the current pin state. |
As far as this task is concerned, below is a possible implementation for a 9-pin RS-232 plug which allows access by pin name or number and provides a comprehensive print out of the current pin state. |
||
< |
<syntaxhighlight lang="ecmascript">import "/seq" for Lst |
||
import "/fmt" for Fmt |
import "/fmt" for Fmt |
||
Line 1,323: | Line 1,323: | ||
plug[3] = ON // set pin 3 by number |
plug[3] = ON // set pin 3 by number |
||
plug["DSR"] = "ON" // set pin 6 by name and using a string |
plug["DSR"] = "ON" // set pin 6 by name and using a string |
||
System.print(plug) // print the state of the pins</ |
System.print(plug) // print the state of the pins</syntaxhighlight> |
||
{{out}} |
{{out}} |
||
Line 1,340: | Line 1,340: | ||
{{trans|6502 Assembly}} |
{{trans|6502 Assembly}} |
||
< |
<syntaxhighlight lang="z80">softRS232_LO equ &C000 ;%87654321 (each bit represents the state of a numbered pin) |
||
softRS232_HI equ &C001 ;%-------9 |
softRS232_HI equ &C001 ;%-------9 |
||
Line 1,348: | Line 1,348: | ||
outi ;send the value contained in softRS232_LO thru port &00 |
outi ;send the value contained in softRS232_LO thru port &00 |
||
outi ;send the value contained in softRS232_HI thru port &00</ |
outi ;send the value contained in softRS232_HI thru port &00</syntaxhighlight> |
||