Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

cross-32 meta-assembler

502 views
Skip to first unread message

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 3:25:26 PM4/17/21
to
Does anyone here use the C32 table-driven cross assembler?

I think Peter Aske was selling it but he seems gone.



--

John Larkin Highland Technology, Inc

The best designs are necessarily accidental.



Ed Lee

unread,
Apr 17, 2021, 3:28:23 PM4/17/21
to
On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> Does anyone here use the C32 table-driven cross assembler?

I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 3:56:30 PM4/17/21
to
I need to revise an old 68332 program. My version of the
cross-assembler is C32C, which runs under XP but not Windows 7, which
is a nuisance. I think there was a C32D version.

A few people seem to sell C32, probably not authorized, but they are
not much help.

Don Y

unread,
Apr 17, 2021, 4:08:11 PM4/17/21
to
On 4/17/2021 12:56 PM, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>> Does anyone here use the C32 table-driven cross assembler?
>>
>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>
> I need to revise an old 68332 program. My version of the
> cross-assembler is C32C, which runs under XP but not Windows 7, which
> is a nuisance. I think there was a C32D version.

Run the application in XP compatibility mode.

Ed Lee

unread,
Apr 17, 2021, 4:12:09 PM4/17/21
to
On Saturday, April 17, 2021 at 12:56:30 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> >> Does anyone here use the C32 table-driven cross assembler?
> >
> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
> I need to revise an old 68332 program. My version of the
> cross-assembler is C32C, which runs under XP but not Windows 7, which
> is a nuisance. I think there was a C32D version.

GCC can handle 683XX. I think the assembler can do it also.

"Use this option for microcontrollers with a CPU32 or CPU32+ core, including the 68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349 and 68360. "

It might have a slightly different mnemonics or syntax. What are the instructions in question?

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 4:21:37 PM4/17/21
to
On Sat, 17 Apr 2021 13:07:55 -0700, Don Y
<blocked...@foo.invalid> wrote:

>On 4/17/2021 12:56 PM, jla...@highlandsniptechnology.com wrote:
>> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>> <edward....@gmail.com> wrote:
>>
>>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>>> Does anyone here use the C32 table-driven cross assembler?
>>>
>>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>>
>> I need to revise an old 68332 program. My version of the
>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>> is a nuisance. I think there was a C32D version.
>
>Run the application in XP compatibility mode.

That doesn't work for some reason.


>
>> A few people seem to sell C32, probably not authorized, but they are
>> not much help.
>>
>>
>>


Don Y

unread,
Apr 17, 2021, 4:24:53 PM4/17/21
to
On 4/17/2021 1:21 PM, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 13:07:55 -0700, Don Y
> <blocked...@foo.invalid> wrote:
>
>> On 4/17/2021 12:56 PM, jla...@highlandsniptechnology.com wrote:
>>> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>>> <edward....@gmail.com> wrote:
>>>
>>>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>>>> Does anyone here use the C32 table-driven cross assembler?
>>>>
>>>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>>>
>>> I need to revise an old 68332 program. My version of the
>>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>>> is a nuisance. I think there was a C32D version.
>>
>> Run the application in XP compatibility mode.
>
> That doesn't work for some reason.

That's an incredibly helpful explanation of the problem you're seeing!

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 4:28:07 PM4/17/21
to
On Sat, 17 Apr 2021 13:12:05 -0700 (PDT), Ed Lee
<edward....@gmail.com> wrote:

>On Saturday, April 17, 2021 at 12:56:30 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>> <edward....@gmail.com> wrote:
>>
>> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>> >> Does anyone here use the C32 table-driven cross assembler?
>> >
>> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>> I need to revise an old 68332 program. My version of the
>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>> is a nuisance. I think there was a C32D version.
>
>GCC can handle 683XX. I think the assembler can do it also.
>
>"Use this option for microcontrollers with a CPU32 or CPU32+ core, including the 68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349 and 68360. "
>
>It might have a slightly different mnemonics or syntax. What are the instructions in question?

Slightly different syntax would be a nightmare. It's 7200 lines of
code.

I have an old Samsung netbook that runs XP and works, but it's a
nuisance, and I'd like a modern solution. We have a number of 68K
based products still in production.

After some decades, the MC68332 is still in production! It has
outlasted generations of ARMs.

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 4:32:18 PM4/17/21
to
On Sat, 17 Apr 2021 13:24:38 -0700, Don Y
It doesn't run in any of the compatibility modes. What more can I say?

Ed Lee

unread,
Apr 17, 2021, 4:34:07 PM4/17/21
to
On Saturday, April 17, 2021 at 1:28:07 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 13:12:05 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
> >On Saturday, April 17, 2021 at 12:56:30 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> >> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> >> <edward....@gmail.com> wrote:
> >>
> >> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> >> >> Does anyone here use the C32 table-driven cross assembler?
> >> >
> >> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
> >> I need to revise an old 68332 program. My version of the
> >> cross-assembler is C32C, which runs under XP but not Windows 7, which
> >> is a nuisance. I think there was a C32D version.
> >
> >GCC can handle 683XX. I think the assembler can do it also.
> >
> >"Use this option for microcontrollers with a CPU32 or CPU32+ core, including the 68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349 and 68360. "
> >
> >It might have a slightly different mnemonics or syntax. What are the instructions in question?
> Slightly different syntax would be a nightmare. It's 7200 lines of
> code.

But it's one-to-one mapping. I believe there is a translator available also.

> I have an old Samsung netbook that runs XP and works, but it's a
> nuisance, and I'd like a modern solution. We have a number of 68K
> based products still in production.

You can compile GCC under Window 7/10.

Don Y

unread,
Apr 17, 2021, 4:35:31 PM4/17/21
to
What do you mean "it doesn't run"? Does the command window *crash*?
Does the application just abend, immediately? Does it not see the input
file you've specified?

Ed Lee

unread,
Apr 17, 2021, 4:48:06 PM4/17/21
to
Compilers/Assemblers are mostly dos mode file I/O anyway. I think it's the limited memory compatibility issues.

Don Y

unread,
Apr 17, 2021, 4:53:55 PM4/17/21
to
The product in question has a GUI mode like a primitive IDE.

If all you want to do is reassemble some existing/modified code,
I suspect the command line version would suffice.

boB

unread,
Apr 17, 2021, 5:25:36 PM4/17/21
to
On Sat, 17 Apr 2021 13:34:04 -0700 (PDT), Ed Lee
<edward....@gmail.com> wrote:

>On Saturday, April 17, 2021 at 1:28:07 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>> On Sat, 17 Apr 2021 13:12:05 -0700 (PDT), Ed Lee
>> <edward....@gmail.com> wrote:
>>
>> >On Saturday, April 17, 2021 at 12:56:30 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>> >> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>> >> <edward....@gmail.com> wrote:
>> >>
>> >> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>> >> >> Does anyone here use the C32 table-driven cross assembler?
>> >> >
>> >> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>> >> I need to revise an old 68332 program. My version of the
>> >> cross-assembler is C32C, which runs under XP but not Windows 7, which
>> >> is a nuisance. I think there was a C32D version.
>> >
>> >GCC can handle 683XX. I think the assembler can do it also.
>> >
>> >"Use this option for microcontrollers with a CPU32 or CPU32+ core, including the 68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349 and 68360. "
>> >
>> >It might have a slightly different mnemonics or syntax. What are the instructions in question?
>> Slightly different syntax would be a nightmare. It's 7200 lines of
>> code.
>
>But it's one-to-one mapping. I believe there is a translator available also.
>
>> I have an old Samsung netbook that runs XP and works, but it's a
>> nuisance, and I'd like a modern solution. We have a number of 68K
>> based products still in production.


Great reason to keep a couple of old computers around !

OR, possibly run an older OS using a virtual machine.

Don Y

unread,
Apr 17, 2021, 5:47:53 PM4/17/21
to
On 4/17/2021 2:25 PM, boB wrote:

>>> I have an old Samsung netbook that runs XP and works, but it's a
>>> nuisance, and I'd like a modern solution. We have a number of 68K
>>> based products still in production.
>
> Great reason to keep a couple of old computers around !

I keep a variety of (hardware) machines around, but mainly
to support hardware devices that were only supported on
particular OSs.

> OR, possibly run an older OS using a virtual machine.

This. I keep a variety of "generic" OS setups on my ESXi
server. When I have a need for some particular old app,
I make a copy of the generic machine (for that guest OS)
and then add whatever tool(s) I happen to need.

If I am likely to need this environment again, then I
save the new machine (coming up with image names gets to
be a chore!) in the hope that I'll remember that I have it
(and what it's called!) at some later date.

Otherwise, delete the machine when I'm done running the
application.

This is an excellent way to test-drive applications
without having to muck up your "real" machines (I don't
completely trust "uninstall")

Hul Tytus

unread,
Apr 17, 2021, 6:00:22 PM4/17/21
to
John - if you find the c32 assembler, especially if you get
the source too, let it be known. I'm working on an assembler
mostly taken from a 68k assembler from the eighties. I've
found 2 and one is working. Dedicated types though; not
a table driven style.

Hul

Lasse Langwadt Christensen

unread,
Apr 17, 2021, 6:06:26 PM4/17/21
to
lørdag den 17. april 2021 kl. 21.56.30 UTC+2 skrev jla...@highlandsniptechnology.com:
> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> >> Does anyone here use the C32 table-driven cross assembler?
> >
> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
> I need to revise an old 68332 program. My version of the
> cross-assembler is C32C, which runs under XP but not Windows 7, which
> is a nuisance. I think there was a C32D version.

install virtualbox and download a winxp image for it

John Doe

unread,
Apr 17, 2021, 6:14:46 PM4/17/21
to
Don Y <blocked...@foo.invalid> wrote:

> This is an excellent way to test-drive applications
> without having to muck up your "real" machines (I don't
> completely trust "uninstall")

More simply, keeping a backup of your Windows installation using Macrium
Reflect does that.

John Doe

unread,
Apr 17, 2021, 6:53:20 PM4/17/21
to
Lasse Langwadt Christensen <lang...@fonz.dk> wrote:

> skrev jla...@highlandsniptechnology.com:
>> Ed Lee <edward....@gmail.com> wrote:
>>> jla...@highlandsniptechnology.com wrote:

>>>> Does anyone here use the C32 table-driven cross assembler?

>>> I think the source code is available for download, but do you have the
>>> hardware to modify? Unless you are building processor with FPGA.

>> I need to revise an old 68332 program. My version of the
>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>> is a nuisance. I think there was a C32D version.

> install virtualbox and download a winxp image for it

Assuming there is no easy fix, that's probably the best solution. There is
an engineer (Paul) in the Windows 10 group that talks lots about
virtualbox.

Also, try "Run as Administrator" in Properties. Also, try installing as
Administrator.

A download link to that program might help.

Joe Gwinn

unread,
Apr 17, 2021, 7:13:25 PM4/17/21
to
On Sat, 17 Apr 2021 13:27:57 -0700, jla...@highlandsniptechnology.com
wrote:

>On Sat, 17 Apr 2021 13:12:05 -0700 (PDT), Ed Lee
><edward....@gmail.com> wrote:
>
>>On Saturday, April 17, 2021 at 12:56:30 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>>> <edward....@gmail.com> wrote:
>>>
>>> >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>> >> Does anyone here use the C32 table-driven cross assembler?
>>> >
>>> >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>>> I need to revise an old 68332 program. My version of the
>>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>>> is a nuisance. I think there was a C32D version.
>>
>>GCC can handle 683XX. I think the assembler can do it also.
>>
>>"Use this option for microcontrollers with a CPU32 or CPU32+ core, including the 68330, 68331, 68332, 68333, 68334, 68336, 68340, 68341, 68349 and 68360. "
>>
>>It might have a slightly different mnemonics or syntax. What are the instructions in question?
>
>Slightly different syntax would be a nightmare. It's 7200 lines of
>code.
>
>I have an old Samsung netbook that runs XP and works, but it's a
>nuisance, and I'd like a modern solution. We have a number of 68K
>based products still in production.
>
>After some decades, the MC68332 is still in production! It has
>outlasted generations of ARMs.

If it's still in production, I'd bet that NXP has or knows of a
suitable toolchain that will handle the legacy C code. It may be
built into gcc these days.

I recall programming the Motorola 68030 back in the day, in assembler
and f77. But it's been a long while.

Joe Gwinn

Don Y

unread,
Apr 17, 2021, 7:31:12 PM4/17/21
to
It's ASM -- hence the issue of worrying about mnemonics, syntax,
macro language, pseudo-ops, etc. Assemblers are far less "standardized"
than HLLs.

Ed Lee

unread,
Apr 17, 2021, 7:40:11 PM4/17/21
to
Motorola had different assembly language syntax. I knew someone working on a translator to GCC before.

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 7:59:56 PM4/17/21
to
On Sat, 17 Apr 2021 22:00:16 +0000 (UTC), Hul Tytus <h...@panix.com>
wrote:

>John - if you find the c32 assembler, especially if you get
>the source too, let it be known. I'm working on an assembler
>mostly taken from a 68k assembler from the eighties. I've
>found 2 and one is working. Dedicated types though; not
>a table driven style.
>
>Hul
>

We modified the 68K definition table to add some 68332 opcodes, and
made a few other tweaks. It would be a nightmare to edit the source
code for some other assembler.

I can run the whole tool chain on the old Samsung XP netbook, but that
involves memory sticks and such, and it may not last forever.

I can recompile all of the tool chain (mostly in PowerBasic) for Win7,
but the C32C cross assembler won't run. I think there was a D version
that would run under Win7.

The Brat just spun the product PCB layout to replace the old Maxim
digital cap, and I need to change the code for that. We plan to build
another thousand boxes, then do a full redesign, with a Zynq or
something, in a year or so.

Several people sell C32C, and one claims to have C32D, but haven't
told me how to order it.

Joe Gwinn

unread,
Apr 17, 2021, 8:02:08 PM4/17/21
to
But Motorola 68000 assembler was standardized, as I recall.

If not, recode the assembler code in C, being line-by-line literal. C
was always accused of being the moral equivalent of assembler, and now
it's a feature, not a bug.

Joe Gwinn

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 8:07:32 PM4/17/21
to
On Sat, 17 Apr 2021 16:40:08 -0700 (PDT), Ed Lee
Source code looks like this:



.SBTTL . RTEMP : READ THE LM71 TEMP SENSOR

; WE READ 14 BITS FROM THE LM71, INTO D4 13:0, AND SIGN-EXTEND
; BIT 13 INTO 15:14. THE RESULT IS A 2'S COMP TEMPERATURE IN
; DEGREES C * 32, WHICH WE THEN SCALE TO DEGC * 10

; PORT D BITS ARE B5 LM71 CS- PIN 70 RUNTIME = 53 USEC
; B2 SCLOCK PIN 67
; B0 SDIN PIN 65


RTEMP: MOVEM.L D1 D4 D5 D7 A0, -(SP) ; SAVE GOODIES

MOVEA.W # PORTD, A0 ; NAVIGATE TO PORT, MATEY
MOVE.W # 2, D1 ; NAME THE SPI CLOCK BIT
BCLR.B D1, (A0) ; AND MAKE SURE CLOCK LINE IS
LOW.

BCLR.B # 5, (A0) ; CHIP SELECT THE NASTY LITTLE
BEAST

CLR.L D4 ; NUKE FUTURE DATA
MOVE.W # 14-1, D7 ; NEED A BIT COUNTER, TOO

LMOP: MOVE.B (A0), D5 ; READ THE PORT AND SHIFT
RIGHT 1 BIT
LSR.B # 1, D5 ; WHICH PUTS SERIAL DATA INTO
X-BIT
ROXL.W # 1, D4 ; SHIFT THAT INTO DATA REG

BSET.B D1, (A0) ; PUMP CLOCK UP
BCLR.B D1, (A0) ; AND DOWN.

DBF D7, LMOP ; - DO 14 BITS -

BSET.B # 5, (A0) ; CHIP DESELECT

BTST.L # 13, D4 ; WAS SIGN BIT SET?
BEQ.S TSCAT ; NO, GO SCALE
ORI.W # B15+B14, D4 ; YES, SIGN EXTEND

TSCAT: MOVE.W D4, TEMPR.W ; SAVE RAW DEGC * 32

; NOW FRACTIONAL MULTIPLY D4 BY 10/32 TO GET DEGS C * 10

K10 = 20480 ; 10/32, AS A FRACTIONAL

MULS.W # K10, D4 ; DO MULT
SWAP.W D4 ; AND MAKE THAT FRACTIONAL
MOVE.W D4, TEMPC.W ; AND STASH IN RAM

MOVEM.L (SP)+, D1 D4 D5 D7 A0 ; UNSAVE GOODIES
RTS

Don Y

unread,
Apr 17, 2021, 8:30:03 PM4/17/21
to
On 4/17/2021 5:01 PM, Joe Gwinn wrote:
> On Sat, 17 Apr 2021 16:30:55 -0700, Don Y

>> It's ASM -- hence the issue of worrying about mnemonics, syntax,
>> macro language, pseudo-ops, etc. Assemblers are far less "standardized"
>> than HLLs.
>
> But Motorola 68000 assembler was standardized, as I recall.

But assembler vendors used their own pseudo-ops, macro languages, etc.
This seemed to be especially true of "lower level" (simpler to build!)
tools like assemblers -- every vendor would try to add value by
augmenting the "language" with their own brand of hooks.

[I used to craft ASLs using the macro language facilities of
many of those tools. Moving to a different vendors tool would
"break" my code (cuz I was relying on the assembler to
*generate* the code for me!)]

I've always found "porting" ASM to be more tedious (not harder, just
tedious) than any other HLL.

> If not, recode the assembler code in C, being line-by-line literal. C
> was always accused of being the moral equivalent of assembler, and now
> it's a feature, not a bug.

7000 lines of ASM is probably less than 1000 lines of C so
a reasonable assumption. If the code already is known to work, then
its probably less than a two week job. Esp as it lets more folks
support the codebase, going forward.

And, gives a cleaner framework in which to add/modify the
functionality.

OTOH, I suspect there are lots of assumptions "between the lines"
in the ASM code that would have to be made more explicit in a C
implementation. I'm considerably "safer" when writing in a HLL
than in ASM (cuz I have to allow for the code generator's
flexibility)

Don Y

unread,
Apr 17, 2021, 8:32:21 PM4/17/21
to
So, all of your commentary just repeats what the code already says.

Learn to use symbolic references and elide all of that cruft!

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 9:07:53 PM4/17/21
to
No, it says what the code does.

>
>Learn to use symbolic references and elide all of that cruft!

Symbolic references? Like PORTD and TEMPC?

Don Y

unread,
Apr 17, 2021, 9:37:57 PM4/17/21
to
Make the CODE say what the code does!

>> Learn to use symbolic references and elide all of that cruft!
>
> Symbolic references? Like PORTD and TEMPC?

Like:

; We iteratively read NUMBER_OF_BITS bits from the LM71 at
; CHIP_SELECT into D4. We then sign-extend by replicating
; the leftmost bit (MSb) to all more-signficant bits.
; The result is a temperature in degrees C * 32 which we
; then scale to K10 * C degrees.

; PORTD bit assignments
CLOCK_SIGNAL = 2
CHIP_SELECT = 5 ; active low
SERIAL_DATA = 0 ; implicit code dependency!

NUMBER_OF_BITS = 14

; add invariant, here: (NUMBER_OF_BITS > 1) && (NUMBER_OF_BITS < 16)
RTEMP: MOVEM.L D1 D4 D5 D7 A0, -(SP)

MOVEA.W # PORTD, A0
MOVE.W # CLOCK_SIGNAL,D1
BCLR.B D1, (A0)

BCLR.B # CHIP_SELECT,(A0)

CLR.L D4
MOVE.W # NUMBER_OF_BITS-1,D7

LMOP: MOVE.B (A0), D5
LSR.B # 1, D5

ROXL.W # 1, D4

BSET.B D1, (A0) ; pulse CLOCK
BCLR.B D1, (A0)

DBF D7, LMOP

BSET.B # CHIP_SELECT, (A0)

BTST.L # NUMBER_OF_BITS-1, D4
BEQ.S TSCAT

ORI.W # B15+B14, D4
---------------------^^^^^^^
this one depends on how clever your assembler is. You can
create the constant symbolically using something like:
~( (1 << NUMBER_OF_BITS) - 1 )

TSCAT: MOVE.W D4, TEMPR.W

; NOW FRACTIONAL MULTIPLY D4 BY 10/32 TO GET DEGS C * 10

; the following assumes your assembler deals with integer math > 16 bit
K10 = 65536 * 10 / 32

MULS.W # K10, D4
SWAP.W D4
MOVE.W D4, TEMPC.W

MOVEM.L (SP)+, D1 D4 D5 D7 A0
RTS


Imagine how you'd have to update your *comments* if NUMBER_OF_BITS changed.
Or, if 10/32 needed to become 9/32. (or, answer the next developer's
question: "where the hell did that magic number come from?") Or,
move the CHIP_SELECT to bit 6. etc.

The next guy is likely not going to remember (or know) all of the places
a "magic number" impacts the code. So, he'll forget one and you'll SOMETIMES
see bogus data.

jla...@highlandsniptechnology.com

unread,
Apr 17, 2021, 11:49:43 PM4/17/21
to
On Sat, 17 Apr 2021 18:37:29 -0700, Don Y
Sure. It wouldn't be an LM71 any more.

I always keep my comments right.

>Or, if 10/32 needed to become 9/32. (or, answer the next developer's
>question: "where the hell did that magic number come from?") Or,
>move the CHIP_SELECT to bit 6. etc.
>
>The next guy is likely not going to remember (or know) all of the places
>a "magic number" impacts the code. So, he'll forget one and you'll SOMETIMES
>see bogus data.

The comments explain what is happening. It's pretty obvious.

I like my hardware and my software to work first pass. Commenting
serves the valuable function of explaining the code to *myself*. It's
a kind of design review, a way to think about it twice.

It works. Argue with that.

olaf

unread,
Apr 18, 2021, 1:15:06 AM4/18/21
to
jla...@highlandsniptechnology.com wrote:

>After some decades, the MC68332 is still in production! It has
>outlasted generations of ARMs.

That surprises me. I used the 68332 in 2000, it was a nice cpu, but
after 20years?

However, you can probably use your compiler/assembler in a virtual
machine. For example I have a complete development-system with WinXP
for Renesas M16C/HEW in a virtual machine and another one for some
older FPGA design. In both cases it is also possible to flash/burn
with the USB-Tools.

BTW: Even the Bullshitsoftware from Xilinx runs on a modern Ryzen7,
well not fast, but acceptable. :-)

Olaf



Don Y

unread,
Apr 18, 2021, 1:27:14 AM4/18/21
to
So, I guess you're saing YOU will be the only one to ever look at this
piece of code?

>> Or, if 10/32 needed to become 9/32. (or, answer the next developer's
>> question: "where the hell did that magic number come from?") Or,
>> move the CHIP_SELECT to bit 6. etc.
>>
>> The next guy is likely not going to remember (or know) all of the places
>> a "magic number" impacts the code. So, he'll forget one and you'll SOMETIMES
>> see bogus data.
>
> The comments explain what is happening. It's pretty obvious.

The code explains what's happening. It's *correct*.

> I like my hardware and my software to work first pass. Commenting
> serves the valuable function of explaining the code to *myself*. It's
> a kind of design review, a way to think about it twice.
>
> It works. Argue with that.

If you only have an audience of one -- yourself -- you can do whatever
you want!

Most of us have to -- and DESIRE -- share our code with others.

Martin Brown

unread,
Apr 18, 2021, 4:19:33 AM4/18/21
to
On 17/04/2021 20:56, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>> Does anyone here use the C32 table-driven cross assembler?
>>
>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>
> I need to revise an old 68332 program. My version of the
> cross-assembler is C32C, which runs under XP but not Windows 7, which
> is a nuisance. I think there was a C32D version.

If you have Win7 pro then you should be able to create an enviroment
close enough for an XP only programme to be quite happy. The other way
would be create a virtual XP machine on your Win 7 box. I have found the
odd installer that won't work at all on Win7 but generally I have been
able to coddle old 'doze software into running OK on a Win7 box.

Control Panel
Programs and features
Run programs made for previous versions of windows

It isn't perfect but it should be good enough.

> A few people seem to sell C32, probably not authorized, but they are
> not much help.


--
Regards,
Martin Brown

Tauno Voipio

unread,
Apr 18, 2021, 5:00:26 AM4/18/21
to
On 17.4.2021 22:56 PM, jla...@highlandsniptechnology.com wrote:
> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>> Does anyone here use the C32 table-driven cross assembler?
>>
>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>
> I need to revise an old 68332 program. My version of the
> cross-assembler is C32C, which runs under XP but not Windows 7, which
> is a nuisance. I think there was a C32D version.
>
> A few people seem to sell C32, probably not authorized, but they are
> not much help.


The GNU toolset (gcc, binutils) knows of M68k, including CPU32.

I don't know if there are already built toolchains for Windowses,
but it should be doable from the GNU sources.

--

-TV


Dimiter_Popoff

unread,
Apr 18, 2021, 8:23:29 AM4/18/21
to
Sounds close enough to Motorola syntax, apart from using spaces as
argument delimiters at times instead of commas only.
IIRC the GCC syntax was as shitty as it could get, no point
considering it.
If you had a dps machine it would be a minimal effort (hours) to
make have this go through my A32 assembler. It does not understand
(sp), just (a7), but the syntax is this.
Then this code will also assemble/compile for power (once it goes
through a32) via vpa.

But I am talking hours from my point of view, 7k lines are not that many
and I have been living in/creating that environment for decades. And we
have yet to put a general purpose dps based machine on the market.

Dimiter

======================================================
Dimiter Popoff, TGI http://www.tgi-sci.com
======================================================
http://www.flickr.com/photos/didi_tgi/

Dimiter_Popoff

unread,
Apr 18, 2021, 8:29:40 AM4/18/21
to
Don, sorry but this is outright wrong. Non-commented code belongs
straight into the dust bin.
The comments do not have to explain how the code works, the programmer
is supposed to understand the language.
The comments however - which belong to every line of code - have to tell
the *story*, so you can follow at a glance *what* is being done.
*How* it is being done may be left to the language, if there are
some tricky parts they should be commented as well.

Ed Lee

unread,
Apr 18, 2021, 8:46:27 AM4/18/21
to
Yes, with Assembler PreProcessor (APP), we can linkin Motorola language with C or other HLLs. I believe i can recreate the APP we were using decades ago. Just by adding '%' to A & D registers and removing L from LCLR/LTST/LSET, we get half of the instructions working. Next step is to double pass it to process macros, and dealing with Address registers. GCC does not use much of the Address registers; so, we have to pre-assemble them directly.

__13_________________RTEMP:_MOVEM.L_%D1_D4_D5_D7_%A0,_-(SP)_
__15________________________MOVEA.W_#_PORTD,_A0_
__16_????_323C_0002_________MOVE.W_#_2,_%D1_
__17______0390______________CLR.B_%D1,_(%A0)_
__19________________________CLR.B_#_5,_(%A0)_
__21_????_4284______________CLR.L_%D4_
__22_????_3E3C_000D_________MOVE.W_#_14-1,_%D7_
__24_????_1A10_______LMOP:__MOVE.B_(%A0),_%D5_
__25_????_E20D______________LSR.B_#_1,_%D5_
__26_????_E354______________ROXL.W_#_1,_%D4_
__28________________________SET.B_%D1,_(%A0)_
__29______0390______________CLR.B_%D1,_(%A0)_
__31________________________DBF_D7,_LMOP_
__33______08D0 0005_________SET.B_#_5,_(%A0)_
__35________________________TST.L_#_13,_%D4_
__36_????_6704______________BEQ.S_TSCAT_
__37_????_0044_0000_________ORI.W_#_B15+B14,_%D4_
__39_????_31C4_0000__TSCAT:_MOVE.W_%D4,_TEMPR.W_
__43________________________K10_=_20480_
__45_????_C9FC_5000_________MULS.W_#_K10,_%D4_
__46_????_4844______________SWAP.W_%D4_
__47_????_31C4_0000_________MOVE.W_%D4,_TEMPC.W_
__49________________________MOVEM.L_(SP)+,_%D1_D4_D5_D7_%A0_
__50_????_4E75______________RTS_

PS: CLR/SET are hand decoded values. Comments are removed to pass GCC

Hul Tytus

unread,
Apr 18, 2021, 10:15:04 AM4/18/21
to
Good luck on getting to work on Windows 7.

Hul

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 10:37:43 AM4/18/21
to
On Sat, 17 Apr 2021 22:26:56 -0700, Don Y
The code doesn't say it's an LM71. The comments do.

>
>> I like my hardware and my software to work first pass. Commenting
>> serves the valuable function of explaining the code to *myself*. It's
>> a kind of design review, a way to think about it twice.
>>
>> It works. Argue with that.
>
>If you only have an audience of one -- yourself -- you can do whatever
>you want!
>
>Most of us have to -- and DESIRE -- share our code with others.

Cool. Post some comparable subroutine that you wrote.

Don Y

unread,
Apr 18, 2021, 10:41:17 AM4/18/21
to
Comments should explain the code (fragment's) goal and methodology.
The code indicates what the code is doing. The comment tells you "why".

Superfluous comments just lead to the potential for a developer to
"debug the comments" instead of the code. And, the comments then must
always be updated to track changes to the code; you now have two
things that must remain in sync instead of just the one.
Exactly. Comments explain "why" and outline the overall goal.

> The comments however - which belong to every line of code - have to tell
> the *story*, so you can follow at a glance *what* is being done.

I think this is a bad practice and a throwback to the
"comment every line" days of ASM programming.

The assembler has mechanisms that allow you to encode meaning in your
choice of symbols. Surely:

MOVE.W # CLOCK_SIGNAL,D1
BCLR.B D1, (A0)
BCLR.B # CHIP_SELECT,(A0)

is more expressive and less prone to error than:

MOVE.W # 2, D1 ; NAME THE SPI CLOCK BIT
BCLR.B D1, (A0) ; AND MAKE SURE CLOCK LINE IS LOW.
BCLR.B # 5, (A0) ; CHIP SELECT THE NASTY LITTLE

which could just as easily have been MISTYPED as:

MOVE.W # 3, D1 ; NAME THE SPI CLOCK BIT
BCLR.B D1, (A0) ; AND MAKE SURE CLOCK LINE IS LOW.
BCLR.B # 4, (A0) ; CHIP SELECT THE NASTY LITTLE

Will the developer remember to verify that the SPI Clock is tied to bit 3
(it isn't!) and the CHIP_SELECT is tied to bit 4 (it isn't!)? Or,
will he happily debug the comments and conclude that the code is
written as it should?

Will he remember that "13" is actually derived from NUMBER_OF_BITS
as are the references to B14 and B15 when he cobbles the "working"
code from this project to handle a similar device elsewhere that
happens to only use 12 bits?

BTST.L # 13, D4 ; WAS SIGN BIT SET?
BEQ.S TSCAT ; NO, GO SCALE
ORI.W # B15+B14, D4 ; YES, SIGN EXTEND

> *How* it is being done may be left to the language, if there are
> some tricky parts they should be commented as well.

The initial block comment should describe what the following code
is doing and why. The skilled ASM programmer should be able
to infer where loop iterators exist in the code, where each
part of the process takes place, etc.

Note that the sole "per line" comment that I've added is
that of "pulse clock" as setting and then clearing a bit
might otherwise cause a developer to pause: "Why undo what
you just did?"

; NOW FRACTIONAL MULTIPLY D4 BY 10/32 TO GET DEGS C * 10

K10 = 20480 ; 10/32, AS A FRACTIONAL

MULS.W # K10, D4 ; DO MULT
SWAP.W D4 ; AND MAKE THAT FRACTIONAL
MOVE.W D4, TEMPC.W ; AND STASH IN RAM

Do you really think these 4 "per line" comments ADD anything to your
understanding of the code -- that isn't already stated in the
first freestanding comment?

Do you raelly think JLs commented code is easier to read than
my version -- if you assume that the comments may NOT accurately
reflect what the code is doing? There's a bug, here -- but the
comments lull you into thinking the code is doing what it should:

BTST.L # 14, D4 ; WAS SIGN BIT SET?
BEQ.S TSCAT ; NO, GO SCALE
ORI.W # B15+B14, D4 ; YES, SIGN EXTEND

I comment "per line" when I am shuffling values around a register file
and need to keep track of what's where. E.g., swapping A7 with A5;
"A7 now points to new stack frame"

Or, if doing something in a very specific way (e.g., choosing one
opcode over another to force or avoid a particular side-effect)

Incorrect comments won't flag a "compile" error. So, you
can release a piece of code with incorrect commentary and not
discover it for "years". The next developer thinks:
"This code has been working for years! Surely this must be
correct?!" (yes, the CODE is, but the comments are still wrong)

I think you might be dealing with the same problem JL is:
it's only *your* eyes on your code, not some other developer(s).
And, you're assuming that next developer will follow your practices,
as you hope the *previous* developer did!

The rest of us have likely had to deal with poorly/incorrectly
commented code where the presence of the comments HINDERS our
understanding of the code: "The comments claim X but the code
is doing Y... which is correct -- if either?"

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 10:42:29 AM4/18/21
to
On Sun, 18 Apr 2021 15:29:33 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:


>>>>
>>>> So, all of your commentary just repeats what the code already says.
>>>
>>> No, it says what the code does.
>>
>> Make the CODE say what the code does!
>
>Don, sorry but this is outright wrong. Non-commented code belongs
>straight into the dust bin.

We document an entire product design, hardware and software, as it's
being developed.

That has both immediate value, making us re-think and share the ideas,
and obvious long-term value.

I know people who are violently opposed to commenting. None that work
for me, of course.

There are programs that strip comments from c programs.

Dimiter_Popoff

unread,
Apr 18, 2021, 10:54:26 AM4/18/21
to
On 4/18/2021 17:42, jla...@highlandsniptechnology.com wrote:
> On Sun, 18 Apr 2021 15:29:33 +0300, Dimiter_Popoff <d...@tgi-sci.com>
> wrote:
>
>
>>>>>
>>>>> So, all of your commentary just repeats what the code already says.
>>>>
>>>> No, it says what the code does.
>>>
>>> Make the CODE say what the code does!
>>
>> Don, sorry but this is outright wrong. Non-commented code belongs
>> straight into the dust bin.
>
> We document an entire product design, hardware and software, as it's
> being developed.
>
> That has both immediate value, making us re-think and share the ideas,
> and obvious long-term value.

The immediate value you are talking about is often understated and more
often simply not understood by people who do not write extensive
comments. It should be obvious that while you explain in plain text what
you are doing you would catch misconceptions before they even make it
into the code - but there we are, most programmers just put the effort
in coding - thinking (wrongly) they are being more efficient like
that.

Dimiter

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 10:56:30 AM4/18/21
to
On Sun, 18 Apr 2021 15:23:23 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:
If I went to the extreme of a new tool set, I'd have to run my rom
compare program to make sure every byte was the same. That's a lot of
work to change a half-page subroutine.

My tool chain makes a DEC-style listing, with a table of contents,
page subtitles, and a nice symbol table. All that works fine. I have a
rom builder too, that gobbles .s28 files from the assembler and .raw
files from the FPGA compiler and pokes checksums and stuff.

Our new stuff is all ARMs and c, which other people do, but we have
legacy products that annoying customers keep buying. Sometimes we have
to make a change, mostly from parts going EOL.

>
>But I am talking hours from my point of view, 7k lines are not that many
>and I have been living in/creating that environment for decades. And we
>have yet to put a general purpose dps based machine on the market.
>
>Dimiter
>
>======================================================
>Dimiter Popoff, TGI http://www.tgi-sci.com
>======================================================
>http://www.flickr.com/photos/didi_tgi/

Nice lady. I like skinny women.

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 11:03:52 AM4/18/21
to
Thanks, but I can't find that on my Win7pro.

I've tried all the options in the program properties/run as old
code things, but it still won't run.

I guess I could buy a few more old XP netbooks and keep them in a
freezer.

Dimiter_Popoff

unread,
Apr 18, 2021, 11:13:17 AM4/18/21
to
On 4/18/2021 17:41, Don Y wrote:
> On 4/18/2021 5:29 AM, Dimiter_Popoff wrote:
>> On 4/18/2021 4:37, Don Y wrote:
> .....
>>>
>>> Make the CODE say what the code does!
>>
>> Don, sorry but this is outright wrong. Non-commented code belongs
>> straight into the dust bin.
>
> Comments should explain the code (fragment's) goal and methodology.
> The code indicates what the code is doing.  The comment tells you "why".
>
> Superfluous comments just lead to the potential for a developer to
> "debug the comments" instead of the code.  And, the comments then must
> always be updated to track changes to the code; you now have two
> things that must remain in sync instead of just the one.

Well I have heard all sort of excuses for writing less comments over
the years. Have a look at say this simple piece of code and tell
me which comment you would remove to improve it.

http://tgi-sci.com/vpaex/fcs.sa

> .....
> Do you raelly think JLs commented code is easier to read than
> my version -- if you assume that the comments may NOT accurately
> reflect what the code is doing?  There's a bug, here -- but the
> comments lull you into thinking the code is doing what it should:
>
>           BTST.L  # 14,    D4             ; WAS SIGN BIT SET?
>           BEQ.S   TSCAT                   ;  NO, GO SCALE
>           ORI.W   # B15+B14, D4           ;  YES, SIGN EXTEND

They make the code no worse and yes, they are easier to read than the
code itself - even by me and I have millions of lines written in
a language these lines are a subset of.
More importantly, they demonstrate the *habit* to comment and thus
think more of *what* you are doing instead of how you are doing it.

Dimiter_Popoff

unread,
Apr 18, 2021, 11:26:57 AM4/18/21
to
On 4/18/2021 17:56, jla...@highlandsniptechnology.com wrote:
> ......
>
> If I went to the extreme of a new tool set, I'd have to run my rom
> compare program to make sure every byte was the same. That's a lot of
> work to change a half-page subroutine.

For that little you might just patch the code - just redirect the
subroutine call to some place new, you must have that much unused
ROM space. Thus your old code will remain unchanged at all, you
will have to worry about the new half page only, can't imagine
it would take you more than a day or two of iterations even
with code that old. If you have no assembler at all to do the half page
I could help, me running it on my dps machine or figuring out
a way so you can do that over the net etc.

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 11:59:35 AM4/18/21
to
On Sun, 18 Apr 2021 18:26:50 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:

>On 4/18/2021 17:56, jla...@highlandsniptechnology.com wrote:
>> ......
>>
>> If I went to the extreme of a new tool set, I'd have to run my rom
>> compare program to make sure every byte was the same. That's a lot of
>> work to change a half-page subroutine.
>
>For that little you might just patch the code - just redirect the
>subroutine call to some place new, you must have that much unused
>ROM space. Thus your old code will remain unchanged at all, you
>will have to worry about the new half page only, can't imagine
>it would take you more than a day or two of iterations even
>with code that old. If you have no assembler at all to do the half page
>I could help, me running it on my dps machine or figuring out
>a way so you can do that over the net etc.
>
>Dimiter

It all runs on the old XP netbook. I'd just like to run it on my Win7
PCs.

It's tragic that IBM picked Intel instead of Motorola for their PC.
The 68K had proper memory management and there was a RISC version,
Coldfire.

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 12:12:58 PM4/18/21
to
On Sun, 18 Apr 2021 18:13:10 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:
Yes. Commenting slows down the process and makes one think about
what's happening. A little more coding time saves a lot more debugging
time; especially bugs that the customer finds.

It's amazing the outright hostility that many people have towards
comments.

Same idea with PCB design; review, read, document, think, get it right
the first time. I know organizations that *plan* for five PCB
iterations, and always use at least that many. It takes them years to
get stuff done, if it does get done.

Dimiter_Popoff

unread,
Apr 18, 2021, 12:28:29 PM4/18/21
to
On 4/18/2021 18:59, jla...@highlandsniptechnology.com wrote:
> On Sun, 18 Apr 2021 18:26:50 +0300, Dimiter_Popoff <d...@tgi-sci.com>
> wrote:
>
>> On 4/18/2021 17:56, jla...@highlandsniptechnology.com wrote:
>>> ......
>>>
>>> If I went to the extreme of a new tool set, I'd have to run my rom
>>> compare program to make sure every byte was the same. That's a lot of
>>> work to change a half-page subroutine.
>>
>> For that little you might just patch the code - just redirect the
>> subroutine call to some place new, you must have that much unused
>> ROM space. Thus your old code will remain unchanged at all, you
>> will have to worry about the new half page only, can't imagine
>> it would take you more than a day or two of iterations even
>> with code that old. If you have no assembler at all to do the half page
>> I could help, me running it on my dps machine or figuring out
>> a way so you can do that over the net etc.
>>
>> Dimiter
>
> It all runs on the old XP netbook. I'd just like to run it on my Win7
> PCs.

Oh so you have no real problem. Just get a spare xp machine etc.
I did run some xp emulation on windows 10, vmware, and it worked - for a
while, then at some point - probably a few updates down the
line - stopped doing what I used it for (non-critical, for me
the windows machines are just browsers/pdf readers, well I do use
ltspice occasionally not having my own equivalent). Might be worth
a try, it ran OK while it did and I am not sure I was not at fault
for it to stop.

>
> It's tragic that IBM picked Intel instead of Motorola for their PC.
> The 68K had proper memory management and there was a RISC version,
> Coldfire.
>

I still have in my arsenal the mcf52211 coldfire, a very useful part.
Did a few things with it. The only advantage ARM have nowadays is
lower power, I have yet to adapt an assembler for some of them
(just the smallest, the rest (1W+) is power (PPC), thankfully still
alive.

I remember Peter Alfke saying IBM chose Intel just because they
had it earlier than Motorola had the 68k, about a year (he was
telling the story how he tried to sell the Z8000 to Jobs IIRC,
being that close to all this makes him a credible source, apart
from him being the guy we remember who knew what he was talking about.

Dimiter




Rhydian

unread,
Apr 18, 2021, 12:41:04 PM4/18/21
to
On Sat, 17 Apr 2021 12:56:20 -0700, jlarkin wrote:

> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> <edward....@gmail.com> wrote:
>
>>On Saturday, April 17, 2021 at 12:25:26 PM UTC-7,
>>jla...@highlandsniptechnology.com wrote:
>>> Does anyone here use the C32 table-driven cross assembler?
>>
>>I think the source code is available for download, but do you have the
>>hardware to modify? Unless you are building processor with FPGA.
>
> I need to revise an old 68332 program. My version of the cross-assembler
> is C32C, which runs under XP but not Windows 7, which is a nuisance. I
> think there was a C32D version.
>
> A few people seem to sell C32, probably not authorized, but they are not
> much help.

An XP virtual machine sounds like the answer. I use VirtualBox to run
some old FPGA tools under XP, works fine including USB access for JTAG
etc.

Not sure how it would cope with older programming hardware that bit-bangs
the lines of a parallel port, I haven't tried that.

The XP virtual machine doesn't have any network access, for obvious
reasons. The FPGA toolchain will run on slightly newer versions of
Windows but I chose XP (with SP3) because it will install on a non-
networked machine and not nag you about activation.

If you have the old 68332 development machine, or an image of its HDD,
hanging around anywhere, there is a tool from VirtualBox that will import
it for you, which saves re-installing everything.

HTH

Dimiter_Popoff

unread,
Apr 18, 2021, 12:46:05 PM4/18/21
to
I have not encountered outright hostility to commenting, just
sloppyness, but then I live a pretty isolated life, especially
last 3 years.

I can imagine people who want to make a product and have just
money and no expertise might plan for 5+ iterations hoping one
day one will work, plenty of human activity goes to waste so
this would be a minor part I guess. I have never been able to
afford a non-working first iteration, had I had one it would
just have killed us as a busyness (being largish projects, like
the nukemans, later the netmca). I am used to take lengthy walks
during which to think things through until I get to drawing
and routing, has worked last.. well, nearly 30 years.
Feels like it all started yesterday.

Dimiter



jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 1:09:00 PM4/18/21
to
On Sun, 18 Apr 2021 19:28:21 +0300, Dimiter_Popoff <d...@tgi-sci.com>
Peter was great, I miss him. I met him when both our heads were inside
a box full of books at the Foothill Electronic Flea Market. I miss
that too.

One story I heard was that IBM thought they could control little Intel
better than big Motorola. And little Microsoft!

Ed Lee

unread,
Apr 18, 2021, 1:55:38 PM4/18/21
to
You don't have to change the source code, but do need to verify the translator output.

I am almost done with translating your subroutine. But not sure about decoding the BCLR/BTST/BSET bit fields. Should it be actual number 5 (0005) or bit position 5 (0020). I.e. second arg of line 38.

https://www.nxp.com/files-static/archives/doc/ref_manual/M68000PRM.pdf

__26_______________ _#_RTEMP:_MOVEM.L_D1_D4_D5_D7_A0,_-(SP)_;_SAVE_GOODIES
__28_______________ _#_
__30_????_307C_0000__#_MOVEA.W_#_PORTD,_A0_;_NAVIGATE_TO_PORT,_MATEY
__32_????_323C_0002__#_MOVE.W_#_2,_D1_;_NAME_THE_SPI_CLOCK_BIT
__34_????_0390_______#_BCLR.B_D1,_(A0)_;_AND_MAKE_SURE_CLOCK_LINE_IS_LOW.
__36_______________ _#_
__38_????_0880_0005__#_BCLR.B_#_5,_(A0)_;_CHIP_SELECT_THE_NASTY_LITTLE_BEAST
__40_______________ _#_
__42_????_4284_______#_CLR.L_D4_;_NUKE_FUTURE_DATA
__44_????_3E3C_000D__#_MOVE.W_#_14-1,_D7_;_NEED_A_BIT_COUNTER,_TOO
__46_______________ _#_
__48_????_1A10_______#_LMOP:_MOVE.B_(A0),_D5_;_READ_THE_PORT_AND_SHIFT_RIGHT_1_BIT
__50_????_E20D_______#_LSR.B_#_1,_D5_;_WHICH_PUTS_SERIAL_DATA_INTO_X-BIT
__52_????_E354_______#_ROXL.W_#_1,_D4_;_SHIFT_THAT_INTO_DATA_REG
__54_______________ _#_
__56_????_03D0_______#_BSET.B_D1,_(A0)_;_PUMP_CLOCK_UP
__58_????_0390_______#_BCLR.B_D1,_(A0)_;_AND_DOWN.
__60_______________ _#_
__62_????_51CF_FFF4__#_DBF_D7,_LMOP_;_-_DO_14_BITS_-
__64_______________ _#_
__66_????_08D0_0005__#_BSET.B_#_5,_(A0)_;_CHIP_DESELECT
__68_______________ _#_
__70_______________ _#_BTST.L_#_13,_D4_;_WAS_SIGN_BIT_SET?
__72_????_6704_______#_BEQ.S_TSCAT_;_NO,_GO_SCALE
__74_????_0044_0000__#_ORI.W_#_B15+B14,_D4_;_YES,_SIGN_EXTEND
__76_______________ _#_
__78_????_31C4_0000__#_TSCAT:_MOVE.W_D4,_TEMPR.W_;_SAVE_RAW_DEGC_*_32
__80_______________ _#_
__82_______________ _#_;_NOW_FRACTIONAL_MULTIPLY_D4_BY_10/32_TO_GET_DEGS_C_*_10
__84_______________ _#_
__86_______________ _#_K10_=_20480_;_10/32,_AS_A_FRACTIONAL
__88_______________ _#_
__90_????_C9FC_5000__#_MULS.W_#_K10,_D4_;_DO_MULT

Dimiter_Popoff

unread,
Apr 18, 2021, 2:18:57 PM4/18/21
to
It is the actual number, 5 in your example, not $20.

Ed Lee

unread,
Apr 18, 2021, 2:20:55 PM4/18/21
to
OK, thanks.

Almost done. Just need to handle the stack push/pop opcodes.

Dimiter_Popoff

unread,
Apr 18, 2021, 2:50:44 PM4/18/21
to
These are the movem.l or movem.w opcodes, they are not just limited
to push/pull. Can be used with mutiple addressing mode, using with
a7 predecrement/postincrement is typically used for push/pull.
The expect a list of register or register ranges, like:
movem.l d1-d7,-(a7) pushes d1, d2, ... d7,
movem.l d1-d3,d5,a0,a3-a5,-(a7)
etc., all valid variations.

Ed Lee

unread,
Apr 18, 2021, 3:03:26 PM4/18/21
to
OK, here is the complete translation/assembly. Yes, i cheated by editing the Push/Pop Save/Unsave Goodies. It's just easier and look better with the output.

___4_______________ _#_.SBTTL_._RTEMP_:_READ_THE_LM71_TEMP_SENSOR
___6_______________ _#_
___8_______________ _#_;_WE_READ_14_BITS_FROM_THE_LM71,_INTO_D4_13:0,_AND_SIGN-EXTEND
__10_______________ _#_;_BIT_13_INTO_15:14._THE_RESULT_IS_A_2'S_COMP_TEMPERATURE_IN
__12_______________ _#_;_DEGREES_C_*_32,_WHICH_WE_THEN_SCALE_TO_DEGC_*_10
__14_______________ _#_
__16_______________ _#_;_PORT_D_BITS_ARE_B5_LM71_CS-_PIN_70_RUNTIME_=_53_USEC
__18_______________ _#_;_B2_SCLOCK_PIN_67
__20_______________ _#_;_B0_SDIN_PIN_65
__22_______________ _#_
__24_______________ _#_
__26_______________ _#_RTEMP:_;_MOVEM.L_D1_D4_D5_D7_A0,_-(SP)_;_SAVE_GOODIES
__28_????_48E7_4000__#_MOVEM.L_D1,_-(%SP)
__30_????_48E7_0800__#_MOVEM.L_D4,_-(%SP)
__32_????_48E7_0400__#_MOVEM.L_D5,_-(%SP)
__34_????_48E7_0100__#_MOVEM.L_D7,_-(%SP)
__36_????_48E7_0080__#_MOVEM.L_A0,_-(%SP)
__38_______________ _#_
__40_????_307C_0000__#_MOVEA.W_#_PORTD,_A0_;_NAVIGATE_TO_PORT,_MATEY
__42_????_323C_0002__#_MOVE.W_#_2,_D1_;_NAME_THE_SPI_CLOCK_BIT
__44_????_0390_______#_BCLR.B_D1,_(A0)_;_AND_MAKE_SURE_CLOCK_LINE_IS_LOW.
__46_______________ _#_
__48_????_0880_0005__#_BCLR.B_#_5,_(A0)_;_CHIP_SELECT_THE_NASTY_LITTLE_BEAST
__50_______________ _#_
__52_????_4284_______#_CLR.L_D4_;_NUKE_FUTURE_DATA
__54_????_3E3C_000D__#_MOVE.W_#_14-1,_D7_;_NEED_A_BIT_COUNTER,_TOO
__56_______________ _#_
__58_????_1A10_______#_LMOP:_MOVE.B_(A0),_D5_;_READ_THE_PORT_AND_SHIFT_RIGHT_1_BIT
__60_????_E20D_______#_LSR.B_#_1,_D5_;_WHICH_PUTS_SERIAL_DATA_INTO_X-BIT
__62_????_E354_______#_ROXL.W_#_1,_D4_;_SHIFT_THAT_INTO_DATA_REG
__64_______________ _#_
__66_????_03D0_______#_BSET.B_D1,_(A0)_;_PUMP_CLOCK_UP
__68_????_0390_______#_BCLR.B_D1,_(A0)_;_AND_DOWN.
__70_______________ _#_
__72_????_51CF_FFF4__#_DBF_D7,_LMOP_;_-_DO_14_BITS_-
__74_______________ _#_
__76_????_08D0_0005__#_BSET.B_#_5,_(A0)_;_CHIP_DESELECT
__78_______________ _#_
__80_????_0804_000D__#_BTST.L_#_13,_D4_;_WAS_SIGN_BIT_SET?
__82_????_6704_______#_BEQ.S_TSCAT_;_NO,_GO_SCALE
__84_????_0044_0000__#_ORI.W_#_B15+B14,_D4_;_YES,_SIGN_EXTEND
__86_______________ _#_
__88_????_31C4_0000__#_TSCAT:_MOVE.W_D4,_TEMPR.W_;_SAVE_RAW_DEGC_*_32
__90_______________ _#_
__92_______________ _#_;_NOW_FRACTIONAL_MULTIPLY_D4_BY_10/32_TO_GET_DEGS_C_*_10
__94_______________ _#_
__96_______________ _#_K10_=_20480_;_10/32,_AS_A_FRACTIONAL
__98_______________ _#_
_100_????_C9FC_5000__#_MULS.W_#_K10,_D4_;_DO_MULT
_102_????_4844_______#_SWAP.W_D4_;_AND_MAKE_THAT_FRACTIONAL
_104_????_31C4_0000__#_MOVE.W_D4,_TEMPC.W_;_AND_STASH_IN_RAM
_106_______________ _#_
_108_______________ _#_;_MOVEM.L_(SP)+,_D1_D4_D5_D7_A0_;_UNSAVE_GOODIES
_110_????_4CF9_0100__#_MOVEM.L_(SP)+,_A0
_112_????_4CF9_0080__#_MOVEM.L_(SP)+,_D7
_114_????_4CF9_0020__#_MOVEM.L_(SP)+,_D5
_116_????_4CF9_0010__#_MOVEM.L_(SP)+,_D4
_118_????_4CF9_0002__#_MOVEM.L_(SP)+,_D1
_120_????_4E75_______#_RTS_

Dimiter_Popoff

unread,
Apr 18, 2021, 3:47:16 PM4/18/21
to
Can you post the script which does this? I am not a gcc user but I have
done things of that sort, like doing the entire HC11 assembler using
macros in my a32 (some 20+ years ago I suppose), some other more
obscure stuff (SDMA opcodes for the 5200 SDMA) etc., would be
curious to look at what yours looks like.
BTW the order by which you push/pull is reversed to the order the 68k
does. Although your push and pull are consistent with each other if
there are accesses to the stacked registers.... :-). The pull order is
d0 first, d7 last, then a0, a1 etc., IOW if you push all registers
you will have d0 at the lowest address and a6 at the highest
(presumably you don't push a7 itself, not impossible BTW).
Oh here, I have uploaded the hc11 macros some time ago:

http://tgi-sci.com/vpaex/hc11.sa


Dimiter

Ed Lee

unread,
Apr 18, 2021, 4:09:11 PM4/18/21
to
I believe the M68K assembler parse them out in the manner i indicated. Left to Right for -(SP) and Right to Left for (SP)+. Even if it's reversed, it should be OK as well.

The rest is done by the following main loop.

main()
{
char *cp, s1[10], s2[10], s3[10], buf[100], buf2[100];
int i;

while(fgets(buf, 100, stdin) > 0)
{
strcpy(buf2, buf);
del_eoln(buf, ';');

cp = strchr(buf, '#');
if(cp && *(cp+1) == ' ')
del_char(cp+1);

s1[0] = 0;
s2[0] = 0;
s3[0] = 0;
sscanf(buf, "%s %s %s", s1, s2, s3);

cp = strchr(buf, 'B');
if(cp)
{
if(!strncmp(cp, "BCLR", 4)
|| !strncmp(cp, "BSET", 4)
|| !strncmp(cp, "BTST", 4)
)
del_char(cp);
}

ins_percent(buf, 'D');
ins_percent(buf, 'A');
ins_percent(buf, 'S');

fputs("# ", stdout);
fputs(buf2, stdout);
if(match(s1, "BCLR.B", s2, "D1,", s3, "(A0)"))
fputs(".word 0x0390\n", stdout);
else if(match(s1, "BSET.B", s2, "D1,", s3, "(A0)"))
fputs(".word 0x03D0\n", stdout);
else if(match(s1, "BCLR.B", s2, "#5,", s3, "(A0)"))
fputs(".word 0x0880, 0x0005\n", stdout);
else if(match(s1, "BSET.B", s2, "#5,", s3, "(A0)"))
fputs(".word 0x08D0, 0x0005\n", stdout);
else if(match(s1, "BTST.L", s2, "#13,", s3, "D4"))
fputs(".word 0x0804, 0x000D\n", stdout);
else
fputs(buf, stdout);
}
}

Don Y

unread,
Apr 18, 2021, 5:43:04 PM4/18/21
to
On 4/18/2021 7:37 AM, jla...@highlandsniptechnology.com wrote:

>> If you only have an audience of one -- yourself -- you can do whatever
>> you want!
>>
>> Most of us have to -- and DESIRE -- share our code with others.
>
> Cool. Post some comparable subroutine that you wrote.

This is from the early 80's (I hardly write ASM, anymore, as it is
such a "low efficiency" language). It ran on a Z80 with limited
resources (a few KB of RAM). It's one of the several "devices"
that the system supported.

"Devices" tend to need access from competing tasks serialized; you
wouldn't want characters emitted by task 1 to be interspersed with
characters emitted by task 5. If a task currently "owns" a device
(simply because he invoked it, first!), you want other tasks trying
to access it to block pending its release (without relying on the
task's code to do that explicitly!)

Typically, you are dealing with abstractions when dealing with a device.
E.g., characters, strings, binary values to be converted to decimal for
display, etc. So, all of the load/store operations that would typically
be involved are superfluous.

Introduction:
LD HL,Name

SEND TO UART
"Hello!"
"My name is "
ISTRING Name
"What's yours?"
IEXIT

; Now, retrieve user's name....

You might also want to share an expensive resource like a floating point
library (recall, this is 8bit vintage hardware) to ensure competing tasks
don't try to intermix operations.

ComputeETA:
SEND TO FPU
ILOAD Distance
IDIV Time
ISTORE Speed
IINV
IMUL TripLength
ISTORE Duration
IEXIT

ShowETA:
SEND TO DISPLAY
"Your ETA is "
IFORMAT FLOAT STYLE1
" minutes."
IEXIT


The "send routine executive" implements this interpreter allowing the code
to be smaller and more abstracted.

What follows is the support for an audio annunciator -- a programmable
counter/timer driving an audio amp behind a low pass filter. A sample use:

LD A,(LEAK_DETECTOR)
CP YES
JNZ NoLeak

LeakDetected:
SEND TO AUDIO
ILDB 5
Loop: ICALL DRIP
REST for 150 counts
IDJNZ Loop
IEXIT

; Do something to ensure the leak gets fixed

NoLeak: ....




DRIP: METRONOME 150*60 BEATS PER MINUTE ;~7ms per beat

BASE_NOTE 0
GUARANTEE GENERATOR IDLE ;ensure FIFO has emptied
GATHER ;get ahead of real-time so queue never starves

PLAY C_NATURAL_4 for 3 counts
PLAY D_NATURAL_4 for 2 counts
PLAY E_NATURAL_4 for 1 count
PLAY F_NATURAL_4 for 1 count
PLAY G_NATURAL_4 for 1 count
PLAY A_NATURAL_4 for 1 count
PLAY B_NATURAL_4 for 1 count

PLAY C_NATURAL_5 for 1 count
PLAY D_NATURAL_5 for 1 count
PLAY E_NATURAL_5 for 1 count
PLAY F_NATURAL_5 for 1 count
PLAY G_NATURAL_5 for 1 count
PLAY A_NATURAL_5 for 1 count
PLAY B_NATURAL_5 for 1 count

RELEASE

IRET


Actual code that *implements* this at:
<https://www.mediafire.com/file/01ddrt90z1lxkde/AUDIO.txt/file>

Note that scant few "lines of code" have comments attached.
Those that do, tend to be there to remind the developer of something
that isn't obvious -- that he will likely BREAK if he's not careful.
E.g.,
OUT (TONCTC),A ;make sure TONCTC is looking at us
OUT (TONCTC),A
gives the impression that one of these OUTs is not needed.
In fact, it is required to guard against a low-likelihood
scenario where the hardware could lock up (which is described in
the OTHER comments). Putting the comment alongside the code is
intended as a flag to the developer: "this is here for a reason!"

All RAM locations are commented.

All EQUs (#defines) are commented.

The entry and exit conditions of each function/subroutine are
commented (I've elided all but one instance as, otherwise, its
a lot of extra text to parse).

The *real* comments happen at the start of each function/subroutine
and "significant code stanza". For example:

SUBTTL AUDIO ANNUNCIATOR DEVICE INTERPRETTER
Page
;AUDIO is invoked to send characters and commands to the audio annunciator
;device by means of the send routine executive interpreter. The audio device
;consists of a preload buffer which holds information for the next tone to be
;generated. This information is derived from the received character/command
;and defines the frequency of the tone to be generated as well as the duration
;of the tone. The send routine executive will interpret the data beginning at
;the address following the call to AUDIO as an interpretive device program.
;Each instruction in this interpretive program represents a character to be sent
;to the audio annunciator device or a high level send routine executive command
;to be executed by the send routine executive on the audio annunciator device.
;If the audio annunciator device is currently assigned to another 'user' all
;other users calling AUDIO will be forced to wait for the device's availability.
;This is accomplished by means of an automatic/implicit multitasking operation
;which redefines the current task's entry point to be the location of the actual
;call to AUDIO. When the device is released, the next waiting AUDIO-caller
;encountered is given control of the device (i.e., send executive standard
operation).

AUDIO: LD IX,AUDICB ;pointer to audio annunciator interpreter control block
JP SNDEXC ;fall into the send routine executive

Has two lines of code and a score lines of prose describing the role
of the device.

The rest of the file describes the ISRs that support that as well as
MACROs used by the developer to write the interpreted code shown earlier.

I contend that adding more "line comments" adds no value for a
developer familiar with the processor (and peripherals). And,
introduces another maintenance issue (cost) as well as opportunity
for error (comments out of sync with code).

Of course, this is a toy application (10KLOC).

I'll be publishing my RTOS, speech synthesizers, gesture recognizer,
time service, applet compiler, IDL compiler, etc. once ALL of them
are ready (presently, only "select colleagues" have access to them
for their development efforts). These range in complexity from
~10KLOC to 100KLOC -- but, in C (so, figure half an order of
magnitude larger in ASM complexity)

I now include even *less* in the codebase -- but, considerably *more*
in supplemental documents. For example, audio sound samples for speech
synthesis, animations for RTOS actions, interactive demos to
highlight how Bezier curves work (a key part of my gesture recognizer
implementation), "enclosed" code snippets, enumerated test cases, etc.

Don Y

unread,
Apr 18, 2021, 5:56:13 PM4/18/21
to
On 4/18/2021 8:13 AM, Dimiter_Popoff wrote:
> On 4/18/2021 17:41, Don Y wrote:
>> On 4/18/2021 5:29 AM, Dimiter_Popoff wrote:
>>> On 4/18/2021 4:37, Don Y wrote:
>> .....
>>>>
>>>> Make the CODE say what the code does!
>>>
>>> Don, sorry but this is outright wrong. Non-commented code belongs
>>> straight into the dust bin.
>>
>> Comments should explain the code (fragment's) goal and methodology.
>> The code indicates what the code is doing. The comment tells you "why".
>>
>> Superfluous comments just lead to the potential for a developer to
>> "debug the comments" instead of the code. And, the comments then must
>> always be updated to track changes to the code; you now have two
>> things that must remain in sync instead of just the one.
>
> Well I have heard all sort of excuses for writing less comments over
> the years. Have a look at say this simple piece of code and tell
> me which comment you would remove to improve it.

I've not advocated writing LESS comments. I've advocated divorcing
them from individual lines of code (because the line of code ALREADY
SAYS WHAT IT IS DOING!) and moving them to a place where they can more
naturally explain what the code is doing.

I've also advocated using symbols instead of hard-coded magic numbers.
These help explain what the particular opcode is doing as well
as telling the next developer the significance of the magic number
AND ensuring that everything RELATED to that magic number is
updated at the same time.

> http://tgi-sci.com/vpaex/fcs.sa

Do you really need to be told "point to next"? Or, "save regs"?
Really? And you've written millions of lines of code???

cmp.l+ #2,d3 16-bit fcs?
bne fcs32 branch not, try 32
fcs16

Gee, you couldn't look at that label and not deduce "not
taking the branch indicates fcs16; TAKING the branch is fcs32
(why did you need to write "branch not, try 32"? Doesn't
BNE indicate that you will be taking a conditional branch to
"fcs32"?)

rts *return*

REALLY??? Do you need to be reminded what RTS stands for??

Describe what you are going to do in the preface to the code body.
All of these little notes don't add anything. They're just clutter,
extra keystrokes and opportunities for them to get out of sync with
the code (which is what the processor will actually EXECUTE!)

>> .....
>> Do you raelly think JLs commented code is easier to read than
>> my version -- if you assume that the comments may NOT accurately
>> reflect what the code is doing? There's a bug, here -- but the
>> comments lull you into thinking the code is doing what it should:
>>
>> BTST.L # 14, D4 ; WAS SIGN BIT SET?
>> BEQ.S TSCAT ; NO, GO SCALE
>> ORI.W # B15+B14, D4 ; YES, SIGN EXTEND
>
> They make the code no worse and yes, they are easier to read than the
> code itself - even by me and I have millions of lines written in
> a language these lines are a subset of.
> More importantly, they demonstrate the *habit* to comment and thus
> think more of *what* you are doing instead of how you are doing it.

Look at the file I uploaded. Tell me which lines of code need
additional clarification (I suspect you can sort out what
each line is doing even if you've never encountered the CPU
before).

By contrast, all of the "prose" I've included adds value. It
tells you what to expect. "Why are there so many ISRs???"

You want to think BEFORE you're writing. Not adding comments
as an afterthought to having written a line of code.

Likewise, you want the next developer to understand what
he's going to encounter without having to try to assemble
a "big picture" out of 20 "half-lines" of commentary.

Dimiter_Popoff

unread,
Apr 18, 2021, 6:36:38 PM4/18/21
to
Save regs I write usually by habit and I see no harm out of that.
Then movem can also do other things, as it often does.

> Really?  And you've written millions of lines of code???
>
>         cmp.l+    #2,d3               16-bit fcs?
>         bne       fcs32               branch not, try 32
> fcs16
>
> Gee, you couldn't look at that label and not deduce "not
> taking the branch indicates fcs16; TAKING the branch is fcs32
> (why did you need to write "branch not, try 32"?  Doesn't
> BNE indicate that you will be taking a conditional branch to
> "fcs32"?)

So how do you determine if the branch is to be taken if the
compare gave an equal result or a not equal one without the
comments. Had you written this without any comment the reader
would have to backtrack who knows where to find out.
I hope you see that you just gave an example why non-commented
this code would be useless.


>
>         rts                           *return*
>
> REALLY???  Do you need to be reminded what RTS stands for??

While I write this out of habit it can (and sometimes does)
have a meaning. Although RTS stands for "return from subroutine"
what it actually does is pull an address from the stack and go
there.
Sometimes this is exactly the most efficient way to *call* an
address, not to return from something. For example, in 68k
land, one might "push efective address" calculated somehow then
do rts to *go* there.


>
> You want to think BEFORE you're writing.  Not adding comments
> as an afterthought to having written a line of code.

You do want to think before writing indeed, sometimes for
months if you will do some "first ever" thing. This is your
strategy. The comments about it belong to paragraphs above
subroutines, at the beginning of files etc.

Then while writing you want to be busy implementing this
strategy in the most efficient way - both in terms of code
and your time spent coding. This is where per line comments come
in - like we both demonstrated using the example with the
cmp/bne above, only you thought you were demonstrating the
opposite :).

>
> Likewise, you want the next developer to understand what
> he's going to encounter without having to try to assemble
> a "big picture" out of 20 "half-lines" of commentary.

If you cannot understand the code by reading *only the comments*
the code is just garbage. Why not write comments per line, because
you cannot not read them if you don't want to or because it is
too much of a typing effort like it used to be 40+ years ago.

Dimiter


Dimiter_Popoff

unread,
Apr 18, 2021, 6:43:49 PM4/18/21
to
On 4/19/2021 1:36, Dimiter_Popoff wrote:

>> Gee, you couldn't look at that label and not deduce "not
>> taking the branch indicates fcs16; TAKING the branch is fcs32
>> (why did you need to write "branch not, try 32"?  Doesn't
>> BNE indicate that you will be taking a conditional branch to
>> "fcs32"?)
>
> So how do you determine if the branch is to be taken if the
> compare gave an equal result or a not equal one without the
> comments. Had you written this without any comment the reader
> would have to backtrack who knows where to find out.
> I hope you see that you just gave an example why non-commented
> this code would be useless.
>

While my point should be obvious I misspoke, "if the branch is to
be taken" should actually read "what taking the branch would
mean", i.e. branch if 16 is wanted or if 32 is wanted.

Dimiter

jla...@highlandsniptechnology.com

unread,
Apr 18, 2021, 7:45:17 PM4/18/21
to
On Mon, 19 Apr 2021 01:36:32 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:
Why would anyone object to "too many comments" ?

Seriously, there is a lot of outright hostility to commenting.

They don't call it "code" for nothing!

Rick C

unread,
Apr 18, 2021, 8:46:22 PM4/18/21
to
On Saturday, April 17, 2021 at 9:37:57 PM UTC-4, Don Y wrote:
> On 4/17/2021 6:07 PM, jla...@highlandsniptechnology.com wrote:
> > On Sat, 17 Apr 2021 17:32:05 -0700, Don Y
> > <blocked...@foo.invalid> wrote:
> >
> >> On 4/17/2021 5:07 PM, jla...@highlandsniptechnology.com wrote:
> >>> BTST.L # 13, D4 ; WAS SIGN BIT SET?
> >>> BEQ.S TSCAT ; NO, GO SCALE
> >>> ORI.W # B15+B14, D4 ; YES, SIGN EXTEND
> >>>
> >>> TSCAT: MOVE.W D4, TEMPR.W ; SAVE RAW DEGC * 32
> >>>
> >>> ; NOW FRACTIONAL MULTIPLY D4 BY 10/32 TO GET DEGS C * 10
> >>>
> >>> K10 = 20480 ; 10/32, AS A FRACTIONAL
> >>>
> >>> MULS.W # K10, D4 ; DO MULT
> >>> SWAP.W D4 ; AND MAKE THAT FRACTIONAL
> >>> MOVE.W D4, TEMPC.W ; AND STASH IN RAM
> >>>
> >>> MOVEM.L (SP)+, D1 D4 D5 D7 A0 ; UNSAVE GOODIES
> >>> RTS
> >>
> >> So, all of your commentary just repeats what the code already says.
> >
> > No, it says what the code does.
> Make the CODE say what the code does!
> >> Learn to use symbolic references and elide all of that cruft!
> >
> > Symbolic references? Like PORTD and TEMPC?
> Like:
>
> ; We iteratively read NUMBER_OF_BITS bits from the LM71 at
> ; CHIP_SELECT into D4. We then sign-extend by replicating
> ; the leftmost bit (MSb) to all more-signficant bits.
> ; The result is a temperature in degrees C * 32 which we
> ; then scale to K10 * C degrees.
>
> ; PORTD bit assignments
> CLOCK_SIGNAL = 2
> CHIP_SELECT = 5 ; active low
> SERIAL_DATA = 0 ; implicit code dependency!

Or just code in a language that is actually portable. Oddly enough Forth is one of the easiest languages to port for embedded targets. It tends to produce very compact code and can actually reside on your target. Use a PC as a terminal with mass storage (think tty with paper tape, but on steroids) and you can use the compiler on the target. You never have to worry about OS updates again.

Porting to a new version of the same processor means you need to touch the serial port interface, maybe. Porting to a new ISA means you need to obtain or write a simple assembler for the few core words coded in assembly. That's actually not a big deal for most processors. The assembler doesn't need to handle every opcode or syntax. You end up with a consistent programming environment across every platform. Very useful. Mecrisp Forth has been ported to many versions of the MSP family and a large number of ARM processors as well as the RISC-V and a custom Forth like processor on FPGAs. It is widespread enough that it has a body of documentation and is becoming the goto Forth for embedded work.

--

Rick C.

- Get 1,000 miles of free Supercharging
- Tesla referral code - https://ts.la/richard11209

Don Y

unread,
Apr 18, 2021, 9:03:16 PM4/18/21
to
On 4/18/2021 4:45 PM, jla...@highlandsniptechnology.com wrote:

> Why would anyone object to "too many comments" ?

Because comments need to be maintained. There is nothing
that the compiler can do to ensure your comments are correct.

> Seriously, there is a lot of outright hostility to commenting.

No, only as to HOW you comment.

> They don't call it "code" for nothing!

I could put a comment on each line of this:

function(int argument) {
int Y = 0;
int X = MAGIC_X;
int current = 0;

for (iteration = 0; iteration < COUNT; iteration++) {
trialX = X;
if (argument > current) {
trialX += (Y >> iteration);
Y -= (X >> iteration);
current -= table[iteration];
} else {
trialX -= (Y >> iteration);
Y += (X >> iteration);
current += table[iteration];
}
X = trialX;
}
}

int table[COUNT] = {
// lots more magic constants
}

and you'd still not understand what it's doing. And it's only a dozen
lines of code!

By contrast, I could describe how it works (with a block
of prose) and you'd not need ANY comments sprinkled in the
code!

Even better, if I wrapped it in an animated "presentation" you'd
not only understand *how* it works but *why* it works! Critical
for anyone who hopes to diddle with it (or the magic numbers within).

Ed Lee

unread,
Apr 18, 2021, 9:27:52 PM4/18/21
to
The APP (Assembler Pre Processor) is a tool to help portings. The OP can mix and match existing codes with HLL like C or fortran, or whatever GCC support. He can call existing assembler codes without arguments and return values. If data passings are necessary, then fix the subroutine to follow the GCC calling conventions.

Latest listing with some fixes:


___2_________________|
___4_________________| .SBTTL . RTEMP : READ THE LM71 TEMP SENSOR
___6_________________|
___8_________________| ; WE READ 14 BITS FROM THE LM71, INTO D4 13:0, AND SIGN-EXTEND
__10_________________| ; BIT 13 INTO 15:14. THE RESULT IS A 2'S COMP TEMPERATURE IN
__12_________________| ; DEGREES C * 32, WHICH WE THEN SCALE TO DEGC * 10
__14_________________|
__16_________________| ; PORT D BITS ARE B5 LM71 CS- PIN 70 RUNTIME = 53 USEC
__18_________________| ; B2 SCLOCK PIN 67
__20_________________| ; B0 SDIN PIN 65
__22_________________|
__24_________________| REGS = 434 ; REG PUSH/POP MAP 0x1B2 A:1 D:10110010
__26_________________| SIGX = 49152 ; SIGN EXTENSION 0xC000 11000000 00000000
__28_________________| K2C = 20480 ; 10/32, AS A FRACTIONAL
__30_________________|
__32_________________| RTEMP: ; MOVEM.L D1 D4 D5 D7 A0, -(SP) ; SAVE GOODIES
__34_0000_48E7_01B2__| MOVEM.L #REGS, -(SP)
__36_________________|
__38_0004_307C_0000__| MOVEA.W # PORTD, A0 ; NAVIGATE TO PORT, MATEY
__40_0008_323C_0002__| MOVE.W # 2, D1 ; NAME THE SPI CLOCK BIT
__42_000c_0390_______| BCLR.B D1, (A0) ; AND MAKE SURE CLOCK LINE IS LOW.
__44_________________|
__46_000e_0880_0005__| BCLR.B # 5, (A0) ; CHIP SELECT THE NASTY LITTLE BEAST
__48_________________|
__50_0012_4284_______| CLR.L D4 ; NUKE FUTURE DATA
__52_0014_3E3C_000D__| MOVE.W # 14-1, D7 ; NEED A BIT COUNTER, TOO
__54_________________|
__56_0018_1A10_______| LMOP: MOVE.B (A0), D5 ; READ THE PORT AND SHIFT RIGHT 1 BIT
__58_001a_E20D_______| LSR.B # 1, D5 ; WHICH PUTS SERIAL DATA INTO X-BIT
__60_001c_E354_______| ROXL.W # 1, D4 ; SHIFT THAT INTO DATA REG
__62_________________|
__64_001e_03D0_______| BSET.B D1, (A0) ; PUMP CLOCK UP
__66_0020_0390_______| BCLR.B D1, (A0) ; AND DOWN.
__68_________________|
__70_0022_51CF_FFF4__| DBF D7, LMOP ; - DO 14 BITS -
__72_________________|
__74_0026_08D0_0005__| BSET.B # 5, (A0) ; CHIP DESELECT
__76_________________|
__78_002a_0804_000D__| BTST.L # 13, D4 ; WAS SIGN BIT SET?
__80_002e_6704_______| BEQ.S TSCAT ; NO, GO SCALE
__82_0030_0044_C000__| ORI.W # SIGX, D4 ; YES, SIGN EXTEND
__84_________________|
__86_0034_31C4_0000__| TSCAT: MOVE.W D4, TEMPR.W ; SAVE RAW DEGC * 32
__88_________________|
__90_________________| ; NOW FRACTIONAL MULTIPLY D4 BY 10/32 TO GET DEGS C * 10
__92_0038_C9FC_5000__| MULS.W # K2C, D4 ; DO MULT
__94_003c_4844_______| SWAP.W D4 ; AND MAKE THAT FRACTIONAL
__96_003e_31C4_0000__| MOVE.W D4, TEMPC.W ; AND STASH IN RAM
__98_________________|
_100_0042_4CDF_01B2__| MOVEM.L (SP)+, #REGS
_102_0046_4E75_______| RTS
_104_________________|

Three Jeeps

unread,
Apr 18, 2021, 9:29:02 PM4/18/21
to
On Saturday, April 17, 2021 at 6:06:26 PM UTC-4, lang...@fonz.dk wrote:
> lørdag den 17. april 2021 kl. 21.56.30 UTC+2 skrev jla...@highlandsniptechnology.com:
> > On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> > <edward....@gmail.com> wrote:
> >
> > >On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> > >> Does anyone here use the C32 table-driven cross assembler?
> > >
> > >I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
> > I need to revise an old 68332 program. My version of the
> > cross-assembler is C32C, which runs under XP but not Windows 7, which
> > is a nuisance. I think there was a C32D version.
> install virtualbox and download a winxp image for it

This is probably the easiest/best soln...
https://archive.org/details/xp51_20191108
Virtual box is *really* handy.....be sure to install the guest additions....

Don Y

unread,
Apr 18, 2021, 9:36:21 PM4/18/21
to
So, you're adding text -- that someone will have to read (and
maintain) when it doesn't really add any value to what the code
itself says!

If I pasted a copy of the Pater Noster in the code (no harm in that!),
would it expedite your understanding of the code? Or, more likely,
would you ask, "Why the hell is this, here?"

>> Really? And you've written millions of lines of code???
>>
>> cmp.l+ #2,d3 16-bit fcs?
>> bne fcs32 branch not, try 32
>> fcs16
>>
>> Gee, you couldn't look at that label and not deduce "not
>> taking the branch indicates fcs16; TAKING the branch is fcs32
>> (why did you need to write "branch not, try 32"? Doesn't
>> BNE indicate that you will be taking a conditional branch to
>> "fcs32"?)
>
> So how do you determine if the branch is to be taken if the
> compare gave an equal result or a not equal one without the
> comments. Had you written this without any comment the reader
> would have to backtrack who knows where to find out.
> I hope you see that you just gave an example why non-commented
> this code would be useless.

The BNE opcode will fall through if the compare fails.
The fall thru case is obviously "fcs16" -- because you've labeled
the next line of code as such.
The branch taken case is obviously "fcs32" -- because you've
specified that label as the target for the branch (which only
applies IF the branch is taken!)

The magic constant ("2") needs to be documented -- why 2 and not 3?
or 8?

Your description of what the code WILL be doing (before the code
body) would make that clear. "WHY would I want to take the fcs16
branch instead of the fcs32 branch? On what criteria would I base
that decision?"

And, wouldn't be limited to ~30 characters tacked onto the end of
a line. (even with resizable windows, no one wants to read really
long lines of source; and, if you ever wanted to render it to
paper, you're forced to deal with linewrap, landscape orientation
or tiny typefaces!)

The lack of space for per-line comments means you end up
adopting cryptic abbreviations so your comment will fit
in the space provided. Or, worse, break your comment into
multiple "line endings". Now, if you insert another
line of code, you're juggling those partial comments:

LD DE,LIMIT ;check to see if r.HL
SBC HL,DE ; has reached its limit

Ooops!

LD DE,LIMIT ;check to see if r.HL
OR A ;clear borrow
SBC HL,DE ; has reached its limit

>> rts *return*
>>
>> REALLY??? Do you need to be reminded what RTS stands for??
>
> While I write this out of habit it can (and sometimes does)
> have a meaning. Although RTS stands for "return from subroutine"
> what it actually does is pull an address from the stack and go
> there.
> Sometimes this is exactly the most efficient way to *call* an
> address, not to return from something. For example, in 68k
> land, one might "push efective address" calculated somehow then
> do rts to *go* there.

Yes. But, I would NOT document the "normal case" and would
only document the exception.

E.g., in the sample code that I uploaded, I included a comment
to "fall into the send routine executive". A micro-efficiency
hack converting:

AUDIO: LD IX,AUDICB ;pointer to audio annunciator interpreter control block
CALL SNDEXC
RET
to:

AUDIO: LD IX,AUDICB ;pointer to audio annunciator interpreter control block
JP SNDEXC ;fall into the send routine executive

The comment is merited because it shows the reason for an unexpected
change in the code. Similarly, the DISPLAY device has a block of
prose with two lines of code:

DISPLAY:LD IX,DSPICB ;pointer to display interpreter control block
JP SNDEXC ;fall into the send routine executive

If I want to return *through* another function/subr, I'd do something
like:
PUSH HL ;TOS saves state of r.HL

;lookup targeted destination address into r.HL

EX (SP),HL ;restore r.HL; TOS gets destination pointer
RET ;return through referenced routine

Note that I would normally *not* document state save/restore code
as it's fairly obvious. But, here, I want to draw attention to the
fact that I have deliberately put r.HL on TOS -- because, I am
(soon) going to put something else in its place and dispatch through
that.

[Ugh! I haven't written Z80 code in decades; apologies if I've
forgotten some mnemonics!]

>> You want to think BEFORE you're writing. Not adding comments
>> as an afterthought to having written a line of code.
>
> You do want to think before writing indeed, sometimes for
> months if you will do some "first ever" thing. This is your
> strategy. The comments about it belong to paragraphs above
> subroutines, at the beginning of files etc.
>
> Then while writing you want to be busy implementing this
> strategy in the most efficient way - both in terms of code
> and your time spent coding. This is where per line comments come
> in - like we both demonstrated using the example with the
> cmp/bne above, only you thought you were demonstrating the
> opposite :).

The code says exactly what you are doing. Presumably, the line
labeled "fcs16" handles the fcs16 case while the line labeled
"fcs32" labels the fcs32 case. The code tells you why the branch
is taken.

>> Likewise, you want the next developer to understand what
>> he's going to encounter without having to try to assemble
>> a "big picture" out of 20 "half-lines" of commentary.
>
> If you cannot understand the code by reading *only the comments*
> the code is just garbage.

I say the opposite: you should be able to understand the code
BY READING THE CODE. I shouldn't need to tell you that I'm
clearing a variable/iterator/counter. You should know that
by noticing the literal "0" being moved into a variable/register.
Or, an equivalent instruction that has the effect of clearing
a register (e.g., XOR with itself) followed by a store.

> Why not write comments per line, because
> you cannot not read them if you don't want to or because it is
> too much of a typing effort like it used to be 40+ years ago.

Note the sheer volume of the comments included in the code
sample I uploaded. How could adding a comment to each line
add any more value?

Martin Brown

unread,
Apr 19, 2021, 4:17:27 AM4/19/21
to
On 18/04/2021 16:03, jla...@highlandsniptechnology.com wrote:
> On Sun, 18 Apr 2021 09:19:24 +0100, Martin Brown
> <'''newspam'''@nonad.co.uk> wrote:
>
>> On 17/04/2021 20:56, jla...@highlandsniptechnology.com wrote:
>>> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
>>> <edward....@gmail.com> wrote:
>>>
>>>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
>>>>> Does anyone here use the C32 table-driven cross assembler?
>>>>
>>>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
>>>
>>> I need to revise an old 68332 program. My version of the
>>> cross-assembler is C32C, which runs under XP but not Windows 7, which
>>> is a nuisance. I think there was a C32D version.
>>
>> If you have Win7 pro then you should be able to create an enviroment
>> close enough for an XP only programme to be quite happy. The other way
>> would be create a virtual XP machine on your Win 7 box. I have found the
>> odd installer that won't work at all on Win7 but generally I have been
>> able to coddle old 'doze software into running OK on a Win7 box.
>>
>> Control Panel
>> Programs and features
>> Run programs made for previous versions of windows
>>
>> It isn't perfect but it should be good enough.
>
> Thanks, but I can't find that on my Win7pro.
>
> I've tried all the options in the program properties/run as old
> code things, but it still won't run.

How won't it run? BSOD or some other error message.

Depending on the vintage of old software it may be dependent on some
prehistoric DOS settings like environment variables and/or want to open
its .ini file with read/write privileges (Win7 won't allow this).

You may have to mess about giving the program (which I assume you trust)
higher level privileges to get it to run. I'd recommend moving the code
to a new directory and allowing it naughty read/write access there.

Simplest approach is create a DOS window with maximum possible
privileges and invoke the errant programme manually from there on the
command line. With any luck you will actually get to see something more
about why it actually refuses to run - maybe enough to fix it.

"Path not found" would be my first guess.

> I guess I could buy a few more old XP netbooks and keep them in a
> freezer.

For software a virtual machine running an old license of XP is usually
good enough. You only need real physical hardware for things that do
bitbanging on parallel ports to drive ancient chip programmers. I
harvest software license keys from physical hardware before I scrap it.

I still have physical hardware around back to Win ME. Quite a lot of my
clients are stuck on Win XP since big scientific instruments have a 25
year lifespan and manufacturers CBA to do drivers for newer OS's. They
would much prefer to sell more (very) expensive new improved hardware.

OS/2 based stuff is now reaching end of life. Great OS - shame about
IBM's piss poor marketing conflating it with the crap PS/2 hardware.

--
Regards,
Martin Brown

Dimiter_Popoff

unread,
Apr 19, 2021, 6:46:10 AM4/19/21
to
On 4/19/2021 4:36, Don Y wrote:
>.....
>>>
>>>          cmp.l+    #2,d3               16-bit fcs?
>>>          bne       fcs32               branch not, try 32
>>> fcs16
>>>
>>> Gee, you couldn't look at that label and not deduce "not
>>> taking the branch indicates fcs16; TAKING the branch is fcs32
>>> (why did you need to write "branch not, try 32"?  Doesn't
>>> BNE indicate that you will be taking a conditional branch to
>>> "fcs32"?)
>>
>> So how do you determine if the branch is to be taken if the
>> compare gave an equal result or a not equal one without the
>> comments. Had you written this without any comment the reader
>> would have to backtrack who knows where to find out.
>> I hope you see that you just gave an example why non-commented
>> this code would be useless.
>
> The BNE opcode will fall through if the compare fails.
> The fall thru case is obviously "fcs16" -- because you've labeled
> the next line of code as such.
> The branch taken case is obviously "fcs32" -- because you've
> specified that label as the target for the branch (which only
> applies IF the branch is taken!)
>
> The magic constant ("2") needs to be documented -- why 2 and not 3?
> or 8?

So you will have to look elsewhere for the documented constant.
Less practical than I wrote it - hopefully this is obvious.
The fact is you understood what I had written at a glance, otherwise
you would not have complained.

When your output is about 150-200kB of source text per month - as mine
has been over the decades - I can only wish you good luck going
back to code you wrote 10-20 years ago. There is no chance you can
remember millions of lines, you read some of the old code as if
someone else has written it.
And I have managed to understand and modify it when necessary,
so my writing style must be comprehensible.
OTOH I have tried to read disassembled code once or twice which
obviously had no comments, it is incomparably harder, trust me.

>
> Your description of what the code WILL be doing (before the code
> body) would make that clear.  "WHY would I want to take the fcs16
> branch instead of the fcs32 branch?  On what criteria would I base
> that decision?"

Or I could write it the way I did and be as efficient as I am.
What now, do you want to compare your efficiency to mine.


> The lack of space for per-line comments means you end up
> adopting cryptic abbreviations so your comment will fit
> in the space provided.

Nonsense. I tend to fit things within 100 columns (an 800 pixels
wide window) and very rarely do I have to extend a line
comment to the line below. And no, my abbreviations are
as cryptic as necessary, usually they fit within 8
characters. The superlong-instead-of-a-comment C style
labelling are impractical (as is C but this is a much longer
story) for many reasons.


>>>          rts                           *return*
>>>
>>> REALLY???  Do you need to be reminded what RTS stands for??
>>
>> While I write this out of habit it can (and sometimes does)
>> have a meaning. Although RTS stands for "return from subroutine"
>> what it actually does is pull an address from the stack and go
>> there.
>> Sometimes this is exactly the most efficient way to *call* an
>> address, not to return from something. For example, in 68k
>> land, one might "push efective address" calculated somehow then
>> do rts to *go* there.
>
> Yes.  But, I would NOT document the "normal case" and would
> only document the exception.

So *why* would you skip the *return* comment, other than making it so
much harder to spot the point of return on that page at a glance.

Dimiter

Ed Lee

unread,
Apr 19, 2021, 7:57:26 AM4/19/21
to
No comment for "comments", but ...

Apparently, for simplicity, GCC does not implement all m68k instructions. For example, just for the BTST.L instuction, there are 32 bits x 8 data registers or 256 translations needed.

__84_002c_0804_000D__| BTST.L #13, D4 ; WAS SIGN BIT SET?

So, we place limitations on register usage, and use D0 only.

__82_002c_3004_______| MOVE D4, D0
__84_002c_0800_000D__| BTST.L #13, D0 ; WAS SIGN BIT SET?

Or just replace D4 with D0.

Similarly, use only A0 for:

__70_001c_08D0_0002__| BSET.B #2, (A0) ; PUMP CLOCK UP
__72_0020_0880_0002__| BCLR.B #2, (A0) ; AND DOWN.

Both MOVEM.Ls are replaced with macro, to make sure they are the same.

__26_________________| REGS = 434 ; REG PUSH/POP MAP 0x1B2 A:1 D:10110010
__44_0000_48E7_01B2__| MOVEM.L #REGS, -(SP)
_108_0046_4CDF_01B2__| MOVEM.L (SP)+, #REGS

Perhaps we need an expansion macro:

REGS = BITMASK(A0,D7,D5,D4,D1);

Got more test codes for me to play with?

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 10:54:55 AM4/19/21
to
On Mon, 19 Apr 2021 09:17:19 +0100, Martin Brown
Windows7 pops up a box and tells me that I should buy a later version
of the program, which is what I'm trying to do.

Don Y

unread,
Apr 19, 2021, 10:59:23 AM4/19/21
to
Why do I care that the constant is "2"? I want to know what it
means/signifies. If it is "37" I'd care no more, nor less.

> The fact is you understood what I had written at a glance, otherwise
> you would not have complained.

I understood it because of the code. I saw "BNE" and recognized a
conditional branch. I saw a target address (label) indicating
the mnemonic YOU had selected to represent the "branch taken"
condition. And, the addition of another label for the "branch not taken"
condition. Hence, deduce "take branch for fcs32, else fcs16".
I don't need a comment for that.

> When your output is about 150-200kB of source text per month - as mine
> has been over the decades - I can only wish you good luck going
> back to code you wrote 10-20 years ago. There is no chance you can
> remember millions of lines, you read some of the old code as if
> someone else has written it.

The code I posted is almost 40 years old. If you had asked me (prior to
digging it up) how it worked, I would have said "a programmable timer
creates square waves that are filtered and amplified". That would
have been the extent of my recollection (and, I suspect if you'd
asked anyone a similar question they'd come up with a similar
GUESSTIMATE).

But, looking through the prose that I wrote, it was clear to me
how the timer was used, how notes were articulated, how I
generated the various constants for each note, how I generated
the "interpretive code" to play melodies, etc. Without
having to read through a series of half-line comments to
piece it all together.

> And I have managed to understand and modify it when necessary,
> so my writing style must be comprehensible.

To you. I can look at code I've written or hardware I've
designed and instantly recognize it as mine. I "know my style".
But, someone else has to be able to read mine -- because I'm
rarely the person who maintains my code.

And, I have to be able to read/understand/maintain code that
has been written by others. I've had to "patch" the code in
several FOSS projects to fix bugs or tweek it to my needs.
So, I'm frequently encountering stuff that has been written
by ??? And, the writer isn't available for me to query.

So, I have to read ALL of the comments "cautiously"; there's
no guarantee that they reflect what the code is actually doing
*or* what it was intended to do.

OTOH, the *code* tells me exactly what the CPU will be doing!
So, that's where my focus inevitably lies.

I think you've been working in a "sheltered" (poor choice of
words) environment for so long that you likely don't realize
what it's like to have to deal with other folks' code,
coding styles, discipline (or lack thereof), etc.

> OTOH I have tried to read disassembled code once or twice which
> obviously had no comments, it is incomparably harder, trust me.

But, it had *no* comments. Not even the blocks of prose that
I've added. Reading decomppiled code for which a symbol table
is available is considerably easier -- you know the names the
developer assigned to variables, functions, etc. If you have
something explaining what each function does, the role of
each variable, etc. you'd not need a "comment per line" to
understand the code.

In the past, I've had compiler vendors not provide sources
for "helper routines", libraries, etc. So, when I'd encounter
a bug in one of those, I'd have to decompile the code to
figure out why it was broken. All I know is the name of
the function (some of which may be documented as standard
library functions).

But, I could look through the machine code and reconstruct
what was happening (early compilers tending to be pretty poor
at optimization). Then, from the reconstructed code, figure
out how to patch the "source" to generate a new binary -- that
would work. Email a copy of the patched source to the
vendor and let HIM figure out how to merge my changes with
the "real" (though still hidden) sources.

>> Your description of what the code WILL be doing (before the code
>> body) would make that clear. "WHY would I want to take the fcs16
>> branch instead of the fcs32 branch? On what criteria would I base
>> that decision?"
>
> Or I could write it the way I did and be as efficient as I am.
> What now, do you want to compare your efficiency to mine.

You and Me don't matter. It's Bob and Elizabeth that we're
concerned with. Both how they can adapt to our particular
coding practices and how we can adapt to theirs.

>> The lack of space for per-line comments means you end up
>> adopting cryptic abbreviations so your comment will fit
>> in the space provided.
>
> Nonsense. I tend to fit things within 100 columns (an 800 pixels
> wide window) and very rarely do I have to extend a line
> comment to the line below. And no, my abbreviations are
> as cryptic as necessary, usually they fit within 8
> characters. The superlong-instead-of-a-comment C style
> labelling are impractical (as is C but this is a much longer
> story) for many reasons.

I fit things in 80 columns. I would rather have 10 windows
open on my screen (5K pixels wide) than one wide window
filled with text.

A statement in a HLL isn't as width-constrained as in ASM.
You can assume your "code" will only eat up ~30 columns;
the rest being available for comment. In a HLL, the
*statement* can span multiple lines. Adding a comment
just makes it more cumbersome.

Let the code explain what it's doing. Write a paragraph
above each "significant stanza" to put what follows into
a context that the reader can understand.

>>>> rts *return*
>>>>
>>>> REALLY??? Do you need to be reminded what RTS stands for??
>>>
>>> While I write this out of habit it can (and sometimes does)
>>> have a meaning. Although RTS stands for "return from subroutine"
>>> what it actually does is pull an address from the stack and go
>>> there.
>>> Sometimes this is exactly the most efficient way to *call* an
>>> address, not to return from something. For example, in 68k
>>> land, one might "push efective address" calculated somehow then
>>> do rts to *go* there.
>>
>> Yes. But, I would NOT document the "normal case" and would
>> only document the exception.
>
> So *why* would you skip the *return* comment, other than making it so
> much harder to spot the point of return on that page at a glance.

How does the comment make the "RTS" stand out? It's yet-another-comment
among a list of such comments.

Again, I say, if YOU are your sole/primary code-consumer, then you only
have to worry about making it easy/efficient for YOU to understand
what you've written.

I build tools that are solely for my own use. How I document them
and support them is entirely under my control -- and, my "problem".

OTOH, I have built tools for others to use. While I have the same
control over how I design/build them, I now have to ensure my
(user) documentation fits THEIR needs. I can't just throw error
codes and have them make sense of these. They won't be interested
in logged minutiae of what's going on inside the code. They want
to know how to *use* it and how to respond to the various types
of situations (which they haven't yet encountered) when they
occur WITHOUT HAVING TO TELEPHONE ME!

The same is true of designs (software and hardware). I could
leave each net in a schematic with it's "default" name
(NETxxxxx). The tools don't care that I've named it
"nChipSelect". And, the circuit will operate the same, regardless
of the representation in the schematic.

Signal names convey meaning to the (human) reader/viewer. If
I know how the circuit works, why bother adding this extra stuff?
Because "I" will likely not be the only consumer of that
documentation.

Labeling EVERY signal isn't necessarily "better". And, you
would likely end up with a mess that has others saying "why the
hell did you label the junction of R26 and Q18?"

OTOH, if it was the *only* such junction labeled, they might
see this as a hint to it having special significance (even
if just labeled as a "test point").

IMO, you want to give people the information they need to
understand a problem; no more and no less. If they don't
understand how a transistor works, there's no amount of
additional information you could add to the schematic to
help them!

Likewise, if they don't understand the instruction set of
the processor (and how the hardware works), then they
shouldn't be looking at the code.

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 11:05:21 AM4/19/21
to
On Mon, 19 Apr 2021 13:46:04 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:
How fast do you code?

Some people average 10 lines per day. I've known people who could do
over 1000, and it usually ran with minimal debugging.

The faster coders do not usually get paid 1000x as much as the slow
ones.

Martin Brown

unread,
Apr 19, 2021, 11:21:51 AM4/19/21
to
You might find it easier and quicker to set up an XP virtual machine.
I'm surprised you haven't got the odd legacy XP PC kicking around. You
should certainly have some legacy activation keys around even if you
have junked the hardware.

One thing that might be relevant is that some older installers with
16bit legacy components don't get on at all with Win7 so you might have
to transplant the executables and settings from a working platform to
get around it. I'd go virtual machine rather than risk the new software
having improvements that get in the way of compiling legacy code. YMMV

--
Regards,
Martin Brown

Don Y

unread,
Apr 19, 2021, 11:26:31 AM4/19/21
to
On 4/19/2021 8:05 AM, jla...@highlandsniptechnology.com wrote:

>> When your output is about 150-200kB of source text per month - as mine
>> has been over the decades - I can only wish you good luck going
>> back to code you wrote 10-20 years ago.
>
> How fast do you code?
>
> Some people average 10 lines per day. I've known people who could do
> over 1000, and it usually ran with minimal debugging.
>
> The faster coders do not usually get paid 1000x as much as the slow
> ones.

Lines of code is a bogus metric. You can generate a lot more
"newlines" in ASM than in a HLL.

What you really want to measure is function points or some other
measure of "progress towards goal". Or, man-months to complete project
of complexity Y.

If I write X lines of code in a HLL and it translates to
KX lines of ASM, should I claim that I write X lines of code?
Or, KX?

I wrote this (posted elsewhere, this thread):

function(int argument) {
int Y = 0;
int X = MAGIC_X;
int current = 0;

for (iteration = 0; iteration < COUNT; iteration++) {
trialX = X;
if (argument > current) {
trialX += (Y >> iteration);
Y -= (X >> iteration);
current -= table[iteration];
} else {
trialX -= (Y >> iteration);
Y += (X >> iteration);
current += table[iteration];
}
X = trialX;
}
}

int table[COUNT] = {
// lots more magic constants
}

"off the top of my head" -- by remembering what the algorithm had to do.
It took me less than two minutes. I'd wager it works, so call it
*debugged* code (a compiler would throw some trivial-to-fix errors
but the code, itself, would work as intended).

Depending on processor (e.g., an old device), that could be 100 ASM statements.
50 lines of code per minute! Wow! <grin>

In reality, it still has to be commented, formally tested, the magic
numbers created and documented, etc. So, now we're up to two *hours*.
(but, still, that would be 200 ASM lines per day!)

Then, of course, the meeting with marketing -- now they want me to use
longs instead of bare ints. Make that 3 hours instead of 2.

And, there's the weekly group status summary meeting (is that today?
it seems like we just HAD one!). So, closer to 4 or 5.

Ooops! Time for lunch. Then a potty break. etc.

This is why productivity is far less than it could be when you
work in a "normal workplace" (and why it can be so much higher
when you *don't*!)

I'd wager Dimiter can spend a dozen UNINTERRUPTED hours writing
code, if he chooses. (and, if you're a night-owl, you don't have
to worry about phone calls and knocks on the door to interrupt
you!)

Don Y

unread,
Apr 19, 2021, 11:33:02 AM4/19/21
to
I suspect he's running x64 W7 and the installer (even in compatibility
mode) just can't cope.

Taking the time (i.e., making the investment) to set up a VM (your choice
of tool) pays big dividends in cases like these. Make a duplicate copy
of a generic machine, install application. Save resulting machine under
a new name.

This is particularly true for older apps where the overhead of the VM
environment reduces "native" performance -- but is still FASTER than the
original application performance!

[I used to support old apps on a Chimera II under Slowaris. Now, it's easier
to just have a boatload of VMs on the ESXi server and access them from *any*
machine.]

Joe Gwinn

unread,
Apr 19, 2021, 11:39:28 AM4/19/21
to
On Mon, 19 Apr 2021 13:46:04 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:

I follow much the same approach as you.

I would summarize my philosophy as the comments tell the intent, not
the design. So, when I'm debugging and see that the intent is not
happening, I know what to look for.

I also use the general comment describing what a section of code does,
plus line by line comments saying what the line is supposed to
achieve, but not how (unless unobvious).

Joe Gwinn

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 11:55:21 AM4/19/21
to
On Mon, 19 Apr 2021 08:26:15 -0700, Don Y
<blocked...@foo.invalid> wrote:

>On 4/19/2021 8:05 AM, jla...@highlandsniptechnology.com wrote:
>
>>> When your output is about 150-200kB of source text per month - as mine
>>> has been over the decades - I can only wish you good luck going
>>> back to code you wrote 10-20 years ago.
>>
>> How fast do you code?
>>
>> Some people average 10 lines per day. I've known people who could do
>> over 1000, and it usually ran with minimal debugging.
>>
>> The faster coders do not usually get paid 1000x as much as the slow
>> ones.
>
>Lines of code is a bogus metric. You can generate a lot more
>"newlines" in ASM than in a HLL.
>
>What you really want to measure is function points or some other
>measure of "progress towards goal". Or, man-months to complete project
>of complexity Y.

Or in Wayne's case, days.

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 11:57:36 AM4/19/21
to
On Mon, 19 Apr 2021 11:39:18 -0400, Joe Gwinn <joeg...@comcast.net>
wrote:
Things like

RTS ; exit with the clock line high

can be useful.

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 12:01:28 PM4/19/21
to
On Mon, 19 Apr 2021 16:21:45 +0100, Martin Brown
My old XP Netbook runs the tool chain, but I'd like to be able to run
it on other machines. I am reluctant to install a bunch of VMs and
such on my working computers.

>
>One thing that might be relevant is that some older installers with
>16bit legacy components don't get on at all with Win7 so you might have
>to transplant the executables and settings from a working platform to
>get around it. I'd go virtual machine rather than risk the new software
>having improvements that get in the way of compiling legacy code. YMMV

If I can get C32D, I can compile an old version and run my rom compare
program to make sure every byte is the same.

Don Y

unread,
Apr 19, 2021, 12:12:32 PM4/19/21
to
Then build an ESXi server and host the OS (and apps) on ONE machine
in your organization. Then, access those machines from any machine
(that has connectivity with the ESXi host).

Personally, I see no problem installing VMware (or VirtualBox) on
EVERY machine and just accessing the actual VMs over the network
(as network shares).

I use the ESXi server for convenience (I know *every* VM is accessible to it).
Performance is suboptimal for a multimedia application; but fine for damn near
everything else!

I also have VMware on each machine so I can mount the VMs (that are on
a SAN that the ESXi server accesses) as network shares and benefit from
better multimedia performance (cuz the code runs on my local machine
instead of using my machine JUST as a "user interface" client).

Finally, I can copy (or create) a LOCAL VM on my current workstation if I
want the best performance of all (assuming every machine -- incl the ESXi
server -- is of comparable performance).

You can spend as much -- or as little -- MONEY as you wish, on these
approaches. But, you *will* have to make an investment of *time*.
In much the same way that you'll have to invest time to "build" a
new laptop with your-favorite-OS-to-host-the-app.

[MS even has their own "solution"]

The difference is, once you've gone the VM route, you can (effectively)
"make a new laptop" in a mouse click.

Dimiter_Popoff

unread,
Apr 19, 2021, 12:15:58 PM4/19/21
to
Here is a line count then a byte count (the latter seems to count
also temporary directories under the one I currently work I usually make
for quick backward reference hence the discrepancy).

http://tgi-sci.com/misc/scnt21.gif

This is since 1994-a or so, all I have written since I think.
Programming takes up 80 or may be 90% of my time, the rest goes on
hardware design for/on which the code is written.
There may be duplicates (other than temp directories) but the
error because of that would be well within 10%.
1.6 million lines in 25 years makes what, about 5k lines per month,
sounds close enough. I am not preoccupied with these figures of
course, had forgotten how to use the scripts I made doing that counting.

1000 lines a day would be a lot, I think I have been there at times
but only when I did not need to think, just program (e.g. when I did
a disassembler for the cpu32 many years ago, I remember this went
very fast but obviously it is a very primitive thing to do).

Dimiter

======================================================
Dimiter Popoff, TGI http://www.tgi-sci.com
======================================================
http://www.flickr.com/photos/didi_tgi/

Dimiter_Popoff

unread,
Apr 19, 2021, 1:00:59 PM4/19/21
to
On 4/19/2021 18:26, Don Y wrote:
> On 4/19/2021 8:05 AM, jla...@highlandsniptechnology.com wrote:
>
>>> When your output is about 150-200kB of source text per month - as mine
>>> has been over the decades - I can only wish you good luck going
>>> back to code you wrote 10-20 years ago.
>>
>> How fast do you code?
>>
>> Some people average 10 lines per day. I've known people who could do
>> over 1000, and it usually ran with minimal debugging.
>>
>> The faster coders do not usually get paid 1000x as much as the slow
>> ones.
>
> Lines of code is a bogus metric.  You can generate a lot more
> "newlines" in ASM than in a HLL.

Depends on which assembler. C is very line hungry, it would take a
either a RISC or some awkward CPU model (like old ones, e.g. the
6800, 8080, 8086) to need more lines for your example below.

> .....
>
> function(int argument) {
>   int Y = 0;
>   int X = MAGIC_X;
>   int current = 0;
>
>   for (iteration = 0; iteration < COUNT; iteration++) {
>      trialX = X;
>      if (argument > current) {
>         trialX += (Y >> iteration);
>         Y -= (X >> iteration);
>         current -= table[iteration];
>      } else {
>         trialX -= (Y >> iteration);
>         Y += (X >> iteration);
>         current += table[iteration];
>      }
>      X = trialX;
>   }
> }
>
> int table[COUNT] = {
>   // lots more magic constants
> }
>

In fact VPA might need less lines than you used in C, 68k
assembly might also be as good.

I seem to agree that line count is not a very precise metric
but then I am not interested in that sort of metrics anyway as
I don't get paid for coding, just for shipping products we
make & deliver.

Dimiter

Don Y

unread,
Apr 19, 2021, 1:15:15 PM4/19/21
to
On 4/19/2021 9:15 AM, Dimiter_Popoff wrote:

> Here is a line count then a byte count (the latter seems to count
> also temporary directories under the one I currently work I usually make for
> quick backward reference hence the discrepancy).
>
> http://tgi-sci.com/misc/scnt21.gif
>
> This is since 1994-a or so, all I have written since I think.
> Programming takes up 80 or may be 90% of my time, the rest goes on
> hardware design for/on which the code is written.
> There may be duplicates (other than temp directories) but the
> error because of that would be well within 10%.
> 1.6 million lines in 25 years makes what, about 5k lines per month,
> sounds close enough. I am not preoccupied with these figures of
> course, had forgotten how to use the scripts I made doing that counting.

What's a line? A line of CODE? Raw comments? Assembler/compiler
directives? A "newline"?

When you count lines, it's really easy to distort measurements.

function(int argument) {
int Y = 0;
int X = MAGIC_X;
int current = 0;

for (iteration = 0; iteration < COUNT; iteration++) {
trialX = X;
if (argument > current) {
trialX += (Y >> iteration);
Y -= (X >> iteration);
current -= table[iteration];
} else {
trialX -= (Y >> iteration);
Y += (X >> iteration);
current += table[iteration];
}
X = trialX;
}
}

This can be seen as ~a dozen lines of code.

I can rewrite it:

function(int argument) {
int Y = 0;
int X = MAGIC_X;
int current = 0;

iteration = 0;
do {
trialX = X;
if (argument > current) {
trialX += (Y >> iteration);
Y -= (X >> iteration);
current -= table[iteration];
} else {
trialX -= (Y >> iteration);
Y += (X >> iteration);
current += table[iteration];
}
X = trialX;
iteration++;
} while iteration < COUNT;
}

and it's 20% "bigger".

Or:

function(int argument) {
int Y = 0;
int X = MAGIC_X;
int current = 0;

for (iteration = 0; iteration < COUNT; iteration++) {
trialX = X;
trialX += (argument > current) ? (Y >> iteration) : -(Y >> iteration);
Y -= (argument > current) ? (X >> iteration) : -(X >> iteration);
current -= (argument > current) ? table[iteration] : -table[iteration];
X = trialX;
}
}

and it's 20% smaller.

The code generated will be exactly the same (for a good compiler).
Some folks will find one version more understandable than others
(I obviously prefer the initial implementation -- for readability).

Should I be rewarded -- or penalized -- for using the number of
semicolons (an easy way to count LoC in C) that I chose? Am
I more or less productive than either of these two alternative
"coders" hypothesized, here?

There's not *quite* as much flexibility in writing ASM (assuming
you don't do silly things like unroll loops needlessly or code
multiplies as shift/add sequences instead of just using a MUL
opcode).

But, there are other aspects that "generate lines" that may
or may not be counted as REAL lines of code.

If I build a macro, it, in itself, represents no PRODUCTION
code. Yet, applying it (likely) generates code. Do I count
each invocation as ONE line of code? Or, do I count the
lines of code that it generates as lines of code (that *I* wrote?)

Following is the interrupt dispatch table from my current project.
How many "lines" should it be regarded? The macro definitions aren't
technically "code" -- even though each creates several lines of
code! Are the invocations counted each as a single line of code,
despite the fact that they each generate ~5 lines of code?

The complexity of the resulting product (i.e., what the host
CPU will actually encounter) doesn't change -- despite the
fact that we can come up with rationalizations for various
LoC interpretations!

Yet, on inspection, you can see how creating such a "piece of code"
can be relatively trivial.


----8<----8<----8<----
/*
* An entry in the Interrupt Descriptor Table.
*/
#define IRQ_ENTRY(vector,flavor) \
.data 2 ;\
.long vector ;\
.word KERNEL_MAGIC ;\
.byte 0 ;\
.byte flavor ;\
.text

/*
* An exception handler entry.
*/
#define EXCEPTION(id,name) \
IRQ_ENTRY(EXT(name),SYS_TRAP_GATE) ;\
MAKE_LABEL(name) ;\
pushl $(0) ;\
pushl $(id) ;\
jmp _svc_trap

/*
* A User Interrupt.
*/
#define EXCEPTION_USER(id,name) \
IRQ_ENTRY(EXT(name),USR_TRAP_GATE);\
MAKE_LABEL(name) ;\
pushl $(0) ;\
pushl $(id) ;\
jmp _svc_trap

/*
* A "Special" interrupt code.
*/
#define EXCEPTION_SPECIAL(id,name) \
IRQ_ENTRY(EXT(name),SYS_TRAP_GATE)

/*
* The error code is already at ToS!
*/
#define EXCEPTION_ERROR(id,name) \
IRQ_ENTRY(EXT(name),SYS_TRAP_GATE);\
MAKE_LABEL(name) ;\
pushl $(id) ;\
jmp _svc_trap

/*
* A "regular" Interrupt Request
*/
#define INTERRUPT(id) \
IRQ_ENTRY(0f,SYS_IRQ_GATE) ;\
0: ;\
pushl %eax ;\
movl $(id),%eax ;\
jmp _svc_irq

.data 2
MAKE_LABEL(idt)

.text

EXCEPTION(0x00,trap_div_by_zero)
EXCEPTION_SPECIAL(0x01,trap_debug)
INTERRUPT(0x02) /* NonMaskable IRQ */
EXCEPTION_USER(0x03,trap_int3)
EXCEPTION_USER(0x04,trap_into)
EXCEPTION_USER(0x05,trap_bounds_check)
EXCEPTION(0x06,trap_illegal_op)
EXCEPTION(0x07,trap_nofpu)
EXCEPTION(0x08,a_double_fault)
EXCEPTION(0x09,a_fpu_over)
EXCEPTION(0x0a,a_invalid_tss)
EXCEPTION_SPECIAL(0x0b,trap_segnp)
EXCEPTION_ERROR(0x0c,trap_stack_fault)
EXCEPTION_SPECIAL(0x0d,trap_protection)
EXCEPTION_SPECIAL(0x0e,trap_page_fault)
EXCEPTION(0x0f,trap_trap_0f)
EXCEPTION(0x10,trap_fpu_error)
EXCEPTION(0x11,trap_trap_11)
EXCEPTION(0x12,trap_trap_12)
EXCEPTION(0x13,trap_trap_13)
EXCEPTION(0x14,trap_trap_14)
EXCEPTION(0x15,trap_trap_15)
EXCEPTION(0x16,trap_trap_16)
EXCEPTION(0x17,trap_trap_17)
EXCEPTION(0x18,trap_trap_18)
EXCEPTION(0x19,trap_trap_19)
EXCEPTION(0x1a,trap_trap_1A)
EXCEPTION(0x1b,trap_trap_1B)
EXCEPTION(0x1c,trap_trap_1C)
EXCEPTION(0x1d,trap_trap_1D)
EXCEPTION(0x1e,trap_trap_1E)
EXCEPTION(0x1f,trap_trap_1F)

INTERRUPT(0x20)
INTERRUPT(0x21)
INTERRUPT(0x22)
INTERRUPT(0x23)
INTERRUPT(0x24)
INTERRUPT(0x25)
INTERRUPT(0x26)
INTERRUPT(0x27)
INTERRUPT(0x28)
INTERRUPT(0x29)
INTERRUPT(0x2a)
INTERRUPT(0x2b)
INTERRUPT(0x2c)
INTERRUPT(0x2d)
INTERRUPT(0x2e)
INTERRUPT(0x2f)

INTERRUPT(0x30)
INTERRUPT(0x31)
INTERRUPT(0x32)
INTERRUPT(0x33)
INTERRUPT(0x34)
INTERRUPT(0x35)
INTERRUPT(0x36)
INTERRUPT(0x37)
INTERRUPT(0x38)
INTERRUPT(0x39)
INTERRUPT(0x3a)
INTERRUPT(0x3b)
INTERRUPT(0x3c)
INTERRUPT(0x3d)
INTERRUPT(0x3e)
INTERRUPT(0x3f)

INTERRUPT(0x40)
INTERRUPT(0x41)
INTERRUPT(0x42)
INTERRUPT(0x43)
INTERRUPT(0x44)
INTERRUPT(0x45)
INTERRUPT(0x46)
INTERRUPT(0x47)
INTERRUPT(0x48)
INTERRUPT(0x49)
INTERRUPT(0x4a)
INTERRUPT(0x4b)
INTERRUPT(0x4c)
INTERRUPT(0x4d)
INTERRUPT(0x4e)
INTERRUPT(0x4f)

INTERRUPT(0x50)
INTERRUPT(0x51)
INTERRUPT(0x52)
INTERRUPT(0x53)
INTERRUPT(0x54)
INTERRUPT(0x55)
INTERRUPT(0x56)
INTERRUPT(0x57)
INTERRUPT(0x58)
INTERRUPT(0x59)
INTERRUPT(0x5a)
INTERRUPT(0x5b)
INTERRUPT(0x5c)
INTERRUPT(0x5d)
INTERRUPT(0x5e)
INTERRUPT(0x5f)

INTERRUPT(0x60)
INTERRUPT(0x61)
INTERRUPT(0x62)
INTERRUPT(0x63)
INTERRUPT(0x64)
INTERRUPT(0x65)
INTERRUPT(0x66)
INTERRUPT(0x67)
INTERRUPT(0x68)
INTERRUPT(0x69)
INTERRUPT(0x6a)
INTERRUPT(0x6b)
INTERRUPT(0x6c)
INTERRUPT(0x6d)
INTERRUPT(0x6e)
INTERRUPT(0x6f)

INTERRUPT(0x70)
INTERRUPT(0x71)
INTERRUPT(0x72)
INTERRUPT(0x73)
INTERRUPT(0x74)
INTERRUPT(0x75)
INTERRUPT(0x76)
INTERRUPT(0x77)
INTERRUPT(0x78)
INTERRUPT(0x79)
INTERRUPT(0x7a)
INTERRUPT(0x7b)
INTERRUPT(0x7c)
INTERRUPT(0x7d)
INTERRUPT(0x7e)
INTERRUPT(0x7f)

INTERRUPT(0x80)
INTERRUPT(0x81)
INTERRUPT(0x82)
INTERRUPT(0x83)
INTERRUPT(0x84)
INTERRUPT(0x85)
INTERRUPT(0x86)
INTERRUPT(0x87)
INTERRUPT(0x88)
INTERRUPT(0x89)
INTERRUPT(0x8a)
INTERRUPT(0x8b)
INTERRUPT(0x8c)
INTERRUPT(0x8d)
INTERRUPT(0x8e)
INTERRUPT(0x8f)

INTERRUPT(0x90)
INTERRUPT(0x91)
INTERRUPT(0x92)
INTERRUPT(0x93)
INTERRUPT(0x94)
INTERRUPT(0x95)
INTERRUPT(0x96)
INTERRUPT(0x97)
INTERRUPT(0x98)
INTERRUPT(0x99)
INTERRUPT(0x9a)
INTERRUPT(0x9b)
INTERRUPT(0x9c)
INTERRUPT(0x9d)
INTERRUPT(0x9e)
INTERRUPT(0x9f)

INTERRUPT(0xa0)
INTERRUPT(0xa1)
INTERRUPT(0xa2)
INTERRUPT(0xa3)
INTERRUPT(0xa4)
INTERRUPT(0xa5)
INTERRUPT(0xa6)
INTERRUPT(0xa7)
INTERRUPT(0xa8)
INTERRUPT(0xa9)
INTERRUPT(0xaa)
INTERRUPT(0xab)
INTERRUPT(0xac)
INTERRUPT(0xad)
INTERRUPT(0xae)
INTERRUPT(0xaf)

INTERRUPT(0xb0)
INTERRUPT(0xb1)
INTERRUPT(0xb2)
INTERRUPT(0xb3)
INTERRUPT(0xb4)
INTERRUPT(0xb5)
INTERRUPT(0xb6)
INTERRUPT(0xb7)
INTERRUPT(0xb8)
INTERRUPT(0xb9)
INTERRUPT(0xba)
INTERRUPT(0xbb)
INTERRUPT(0xbc)
INTERRUPT(0xbd)
INTERRUPT(0xbe)
INTERRUPT(0xbf)

INTERRUPT(0xc0)
INTERRUPT(0xc1)
INTERRUPT(0xc2)
INTERRUPT(0xc3)
INTERRUPT(0xc4)
INTERRUPT(0xc5)
INTERRUPT(0xc6)
INTERRUPT(0xc7)
INTERRUPT(0xc8)
INTERRUPT(0xc9)
INTERRUPT(0xca)
INTERRUPT(0xcb)
INTERRUPT(0xcc)
INTERRUPT(0xcd)
INTERRUPT(0xce)
INTERRUPT(0xcf)

INTERRUPT(0xd0)
INTERRUPT(0xd1)
INTERRUPT(0xd2)
INTERRUPT(0xd3)
INTERRUPT(0xd4)
INTERRUPT(0xd5)
INTERRUPT(0xd6)
INTERRUPT(0xd7)
INTERRUPT(0xd8)
INTERRUPT(0xd9)
INTERRUPT(0xda)
INTERRUPT(0xdb)
INTERRUPT(0xdc)
INTERRUPT(0xdd)
INTERRUPT(0xde)
INTERRUPT(0xdf)

INTERRUPT(0xe0)
INTERRUPT(0xe1)
INTERRUPT(0xe2)
INTERRUPT(0xe3)
INTERRUPT(0xe4)
INTERRUPT(0xe5)
INTERRUPT(0xe6)
INTERRUPT(0xe7)
INTERRUPT(0xe8)
INTERRUPT(0xe9)
INTERRUPT(0xea)
INTERRUPT(0xeb)
INTERRUPT(0xec)
INTERRUPT(0xed)
INTERRUPT(0xee)
INTERRUPT(0xef)

INTERRUPT(0xf0)
INTERRUPT(0xf1)
INTERRUPT(0xf2)
INTERRUPT(0xf3)
INTERRUPT(0xf4)
INTERRUPT(0xf5)
INTERRUPT(0xf6)
INTERRUPT(0xf7)
INTERRUPT(0xf8)
INTERRUPT(0xf9)
INTERRUPT(0xfa)
INTERRUPT(0xfb)
INTERRUPT(0xfc)
INTERRUPT(0xfd)
INTERRUPT(0xfe)
INTERRUPT(0xff)

JM

unread,
Apr 19, 2021, 1:25:34 PM4/19/21
to
On 17/04/2021 20:25, jla...@highlandsniptechnology.com wrote:
> Does anyone here use the C32 table-driven cross assembler?
>
> I think Peter Aske was selling it but he seems gone.
>
>
>

I have version 4, which was the last available - it will run in Win 7.

Don Y

unread,
Apr 19, 2021, 1:27:01 PM4/19/21
to
You're making assumptions about the host processor. An 8b CPU
might take lots of "lines of code". A 32b processor might,
as well -- if I decide that int is really "long long".

But, the actual algorithm won't change. It's *complexity* is constant
yet the amount of code that it generates can change dramatically.

> I seem to agree that line count is not a very precise metric
> but then I am not interested in that sort of metrics anyway as
> I don't get paid for coding, just for shipping products we
> make & deliver.

Exactly. LoC is like counting patents. It says nothing about
the MERIT of the work that went into the effort! Consider the
impact Salk had on society...

LoC is essentially a zeroth order measure of how fast you can type. :>

LoC was intended as a (naive) measure of "coding effort". And,
from there, abused into a productivity measure.

[I had an office mate who was "in the lab" building his first
prototype within a week or two of being hired. By contrast,
I sat at my desk for almost 6 months. When I finally went into
the lab, my design was up and running as soon as it was
fabricated. By contrast, my office mate was still hammering
out the bugs on his Nth prototype iteration. Was I more
productive than he? Or, he than me? Neither. Two completely
different problems -- as well as different design philosophies
(I want to test my designs in my head, not in the lab!)]

If I can mow a lawn in 30 minutes and the lawns you mow take
you 40 minutes, am I *better* than you (at mowing lawns)?
Do I have a *better* lawn mower?

Or, are my lawns different (in some way) than yours? (e.g.,
the folks who call you wait until the grass is a foot deep
and a real chore to mow -- and then RAKE!) In which case,
using time to measure the complexity of the problem or the
efficacy of the solution is just silly.

Dimiter_Popoff

unread,
Apr 19, 2021, 1:34:58 PM4/19/21
to
Notice that my line count is an average over 25 years and while
you might find a lookup table or two consisting of many lines
it all works quite well so it can't be just that. In fact the average
line length comes at 36 characters, it is there to see.

Now show me the line count and average line length of *your* C
code of last at least 10 years if you want us to continue this nonsense.
If you manage to get more than 15 characters per line I'll
be very very surprised (count each CR, not just non-null lines).

To get a taste of what my code looks like (looked like some
10 years ago when I posted these) have a look at
http://tgi-sci.com/vpaex/ , most of the code is more like
20 years old but will give you an idea.

Nowadays - as I get more and more experienced into using the
object system I have designed into dps, the way it learns
new object types etc. things get higher level overall, but the
style has not changed that much.

jla...@highlandsniptechnology.com

unread,
Apr 19, 2021, 1:35:22 PM4/19/21
to
On Mon, 19 Apr 2021 18:25:23 +0100, JM <dontreply...@gmail.com>
wrote:
Can I get a copy of V4, probably C32D.exe? I'd be happy to pay for it,
but I haven't found it for sale anywhere. The author, Peter Aske,
seems to be gone.

I'll donate $100 to your favorite charity or something.

I have a nice tool chain around the assembler, for the 68332. New
opcode table, source preprocessor, listing post-processor, rom image
builder (68K and Xilinx code), rom compare, things like that. They are
available if anyone is interested.

JM

unread,
Apr 19, 2021, 2:35:39 PM4/19/21
to
On 19/04/2021 18:35, jla...@highlandsniptechnology.com wrote:
> On Mon, 19 Apr 2021 18:25:23 +0100, JM <dontreply...@gmail.com>
> wrote:
>
>> On 17/04/2021 20:25, jla...@highlandsniptechnology.com wrote:
>>> Does anyone here use the C32 table-driven cross assembler?
>>>
>>> I think Peter Aske was selling it but he seems gone.
>>>
>>>
>>>
>>
>> I have version 4, which was the last available - it will run in Win 7.
>
> Can I get a copy of V4, probably C32D.exe? I'd be happy to pay for it,
> but I haven't found it for sale anywhere. The author, Peter Aske,
> seems to be gone.
>
> I'll donate $100 to your favorite charity or something.
>
> I have a nice tool chain around the assembler, for the 68332. New
> opcode table, source preprocessor, listing post-processor, rom image
> builder (68K and Xilinx code), rom compare, things like that. They are
> available if anyone is interested.
>
>
>

Yes, I'll dig out the install CD and send you an image to keep you going
(until you can purchase your own version).

WangoTango

unread,
Apr 19, 2021, 2:51:23 PM4/19/21
to
In article <kpgm7glel4afr9nva...@4ax.com>,
jla...@highlandsniptechnology.com says...
> On Sat, 17 Apr 2021 13:07:55 -0700, Don Y
> <blocked...@foo.invalid> wrote:
>
> >On 4/17/2021 12:56 PM, jla...@highlandsniptechnology.com wrote:
> >> On Sat, 17 Apr 2021 12:28:20 -0700 (PDT), Ed Lee
> >> <edward....@gmail.com> wrote:
> >>
> >>> On Saturday, April 17, 2021 at 12:25:26 PM UTC-7, jla...@highlandsniptechnology.com wrote:
> >>>> Does anyone here use the C32 table-driven cross assembler?
> >>>
> >>> I think the source code is available for download, but do you have the hardware to modify? Unless you are building processor with FPGA.
> >>
> >> I need to revise an old 68332 program. My version of the
> >> cross-assembler is C32C, which runs under XP but not Windows 7, which
> >> is a nuisance. I think there was a C32D version.
> >
> >Run the application in XP compatibility mode.
>
> That doesn't work for some reason.
>

I run both his XD and C32 in DOS box.

Joe Gwinn

unread,
Apr 19, 2021, 3:30:23 PM4/19/21
to
On Mon, 19 Apr 2021 08:57:27 -0700, jla...@highlandsniptechnology.com
wrote:

>On Mon, 19 Apr 2021 11:39:18 -0400, Joe Gwinn <joeg...@comcast.net>
>wrote:
>
>>On Mon, 19 Apr 2021 13:46:04 +0300, Dimiter_Popoff <d...@tgi-sci.com>
>>wrote:
>>
[snip]
>>>
>>>So *why* would you skip the *return* comment, other than making it so
>>>much harder to spot the point of return on that page at a glance.
>>
>>I follow much the same approach as you.
>>
>>I would summarize my philosophy as the comments tell the intent, not
>>the design. So, when I'm debugging and see that the intent is not
>>happening, I know what to look for.
>>
>>I also use the general comment describing what a section of code does,
>>plus line by line comments saying what the line is supposed to
>>achieve, but not how (unless unobvious).
>>
>>Joe Gwinn
>
>Things like
>
> RTS ; exit with the clock line high
>
>can be useful.

Yes. Exactly. A critical detail, soon forgotten.

Joe Gwinn

Ed Lee

unread,
Apr 19, 2021, 3:36:41 PM4/19/21
to
But Chip Select disabled, which is even more critical. The clock line is driven low before the chip Chip Select is enabled.

Don Y

unread,
Apr 19, 2021, 3:45:29 PM4/19/21
to
On 4/19/2021 10:34 AM, Dimiter_Popoff wrote:

>>> 1000 lines a day would be a lot, I think I have been there at times
>>> but only when I did not need to think, just program (e.g. when I did
>>> a disassembler for the cpu32 many years ago, I remember this went
>>> very fast but obviously it is a very primitive thing to do).
>
> Notice that my line count is an average over 25 years and while
> you might find a lookup table or two consisting of many lines
> it all works quite well so it can't be just that. In fact the average
> line length comes at 36 characters, it is there to see.

My point was that line count has no real definition. Are you trying
to measure "coding effort"? Algorithm complexity? Language efficiency?
Programmer value?

> Now show me the line count and average line length of *your* C
> code of last at least 10 years if you want us to continue this nonsense.
> If you manage to get more than 15 characters per line I'll
> be very very surprised (count each CR, not just non-null lines).

I'd be penalized because I use lots of whitespace and "free-standing
braces". But, that doesn't mean my code is more -- or less -- efficient.
Nor that I, as a programmer, am more or less effective.

OTOH, I'd gain points for paragraphs of prose (unless you want to explicitly
ignore comments).

> To get a taste of what my code looks like (looked like some
> 10 years ago when I posted these) have a look at
> http://tgi-sci.com/vpaex/ , most of the code is more like
> 20 years old but will give you an idea.
>
> Nowadays - as I get more and more experienced into using the
> object system I have designed into dps, the way it learns
> new object types etc. things get higher level overall, but the
> style has not changed that much.

My current system relies on code generators to create code
for objects and interfaces from specifications. Again,
how would you count lines? Do you count the (few) lines
in the specification? Or, the many lines of generated code?
Or, the even greater number of machine opcodes emitted?

The effort that goes into writing an IDL compiler doesn't count
towards the size of the "product code". Yet, its an effort,
nonetheless.

If there are lots of interfaces (object types), it can represent
a productivity enhancer (cuz it will have the opportunity to
generate lots more code than if it was only used to support
a dozen types).

OTOH, what value to the fact that future developers can simply
mimic an interface specification and know that the correct
code will be generated?

When you are the sole consumer of your product (in this case,
code), you use different criteria to drive your style than when
you are "coding for others". E.g., most folks write comments
for themselves -- not explicitly for "the next guy". So, all
of their assumptions and knowledge is implicit in their
choice of comments.

How often do you see a project that sits down and says, "Dear
Reader" -- and then commences to educate them on the product
they are developing/maintaining?

Pick a FOSS project (i.e., something YOU have no prior experience
with but one that has sources available). Try to figure out what
it's doing -- to a degree where you can make a meaningful change
to the code.

Pick up a colleague's sources for a product/appliance. Try to find
the first instruction that gets executed (!). Then, try to find
any documentation that would have told you where to find it! :-/

The developer KNOWS which files/modules do whatever. He *knows*
where the code starts up. It never occurs to him to document
that for the next guy to come along...

These are the problems that I try to solve with my documentation
and coding style. So, The Next Guy has a head start *and* the
benefit of my perspective -- even if he develops a DIFFERENT
perspective, once he's got his hands dirty.

[I figure I'm doing pretty good, in this regard, as there are
several people (remotely) using my current codebase and I can
count the number of questions I've fielded on one hand!]

Don Y

unread,
Apr 19, 2021, 3:55:57 PM4/19/21
to
On 4/19/2021 12:36 PM, Ed Lee wrote:
> On Monday, April 19, 2021 at 12:30:23 PM UTC-7, Joe Gwinn wrote:
>> On Mon, 19 Apr 2021 08:57:27 -0700, jla...@highlandsniptechnology.com

>>> Things like
>>>
>>> RTS ; exit with the clock line high
>>>
>>> can be useful.
>> Yes. Exactly. A critical detail, soon forgotten.
>
> But Chip Select disabled, which is even more critical. The clock line is
> driven low before the chip Chip Select is enabled.

All of this should be specified in the function's INTERFACE definition.
You shouldn't have to dig through an implementation to figure out what
a piece of code (function) expects for inputs and yields for outputs
(incl side-effects).

The code also didn't alter the operating mode of the LM17. Wasn't
*that* worth noting? (if it had, then the machine might function
differently).

Or, the fact that the width of the clock pulse was defined by the CPU's
clock frequency? And, that it would change if you changed that freq?
(likewise setup and hold times).

John Larkin

unread,
Apr 19, 2021, 4:08:04 PM4/19/21
to
The IXYS digital cap chip (the new part in my project) has clock and
data pins. It bangs an 11-bit shift register directly with no chip
select. It requires that the clock be high at the end of loading.

Well, it's not as weird as the Maxim we're replacing. Its two pins
were CLEAR and COUNT.

John Larkin

unread,
Apr 19, 2021, 4:10:11 PM4/19/21
to
On Mon, 19 Apr 2021 19:35:27 +0100, JM <dontreply...@gmail.com>
That would be great. A couple of people sell the old version, possibly
unauthorized. I've emailed them with no response so far.



Dimiter_Popoff

unread,
Apr 19, 2021, 4:21:41 PM4/19/21
to
On 4/19/2021 22:45, Don Y wrote:
> On 4/19/2021 10:34 AM, Dimiter_Popoff wrote:
>
>>>> 1000 lines a day would be a lot, I think I have been there at times
>>>> but only when I did not need to think, just program (e.g. when I did
>>>> a disassembler for the cpu32 many years ago, I remember this went
>>>> very fast but obviously it is a very primitive thing to do).
>>
>> Notice that my line count is an average over 25 years and while
>> you might find a lookup table or two consisting of many lines
>> it all works quite well so it can't be just that. In fact the average
>> line length comes at 36 characters, it is there to see.
>
> My point was that line count has no real definition.  Are you trying
> to measure "coding effort"?  Algorithm complexity?  Language efficiency?
> Programmer value?

But it does. It is not a precise measure but you count the lines you
have written while programming, whether they are comments or you have
typed in a series of constants or you have been writing code which
runs, it is all part of the effort. Nobody counts their usenet posts
or whatever.
So it is a good measure, the margin of error is likely within 100%,
i.e. someone may have twice the line count of someone else and not
be more efficient. In fact the error is probably way below that.
Average line length can also help against too many null lines.

>
>> Now show me the line count and average line length of *your* C
>> code of last at least 10 years if you want us to continue this nonsense.
>> If you manage to get more than 15 characters per line I'll
>> be very very surprised (count each CR, not just non-null lines).
>
> I'd be penalized because I use lots of whitespace and "free-standing
> braces".  But, that doesn't mean my code is more -- or less -- efficient.
> Nor that I, as a programmer, am more or less effective.
>
> OTOH, I'd gain points for paragraphs of prose (unless you want to
> explicitly
> ignore comments).

I counted all text I have written into sources, comments included.
I also write headers when necessary, I am careful to manage their length
so that they say enough but are not too long to put you off from
reading them - so this would be a fair comparison.
The free standing braces are a disadvantage you will have to swallow,
it was your choice to go C.

Here is a typical header for some call (lower complexity calls take
less word/lines, obviously):

http://tgi-sci.com/misc/fetchx.gif

Joe Gwinn

unread,
Apr 19, 2021, 4:57:08 PM4/19/21
to
On Mon, 19 Apr 2021 23:21:36 +0300, Dimiter_Popoff <d...@tgi-sci.com>
wrote:
My definition of SLOC (source lines of code) is predicated on use for
estimation of human effort to produce said code:

A SLOC is a line:

- Intended to be compiled and executed by a computer (not a word
processor)

- Written by a human (so macro invocations count, but macro expansions
don't count)

- Vulnerable to error (so comments don't count, but for instance data
statements do count)

What measure of code complexity best captured human effort was the
subject of much discussion and invention twenty years ago, but it
turned out that SLOCs works as well as anything, and was the simplest
to measure, so SLOCs won.


Although there are programs for counting SLOCs in all programming
languages, for programs written in C/C++, counting semicolons is a
pretty good way to determine SLOCs.

Joe Gwinn
It is loading more messages.
0 new messages