Sunday, November 8, 2009

Gnome sweet Ohm


This is the back view of my contraption:

This morning, I spent a couple of hours unsuccessfully trying to get my piezo running from within the main interrupt at varying frequencies, and not getting anything. Finally, I traced it down to my having used the "=" operator instead of the "==" equality tester. In the B.A.C.I.C. variants, "=" is multi purpose, and I'd forgotten about that significant difference in C!

Following from that, I wrote some code to beep at a different frequency when each limit was reached, during which I found I had two sensor wires swapped on my Z axis, which was still unattached.

Next, I added in some simple code to zero my "actual" values for each axis on encountering the end stop.

Here's where I found another little thing that had to be done: If you are already interrupting a beam, then you don't know how far the vane has penetrated the slot... so I had to write some backing off code for each axis.. trivial. Problem was, my code to zero the "actual" value counters was working, so I had to write some override code to make the interrupt checks ignore the beam interruption during the backing off period.

Next, I wanted to have the x and y axis the same as you would draw on graph paper, i.e. values increasing from left to right, and front to back. However, although I have bidirectional end vanes on x and y axis, my y axis, in the max frontal extension position, knocks my keyboard from it's parking perch where I program from. Since many builds will be small ones, I decided to change perspective, and have the y zero point at the back, as if viewed from the circuitboard side.

It might not sound like a lot of progress, but it's all these small steps that contribute to a final working CNC router, printer, or automated gizmo.

Friday, November 6, 2009

Dr Frankenstein is pleased with his mutant creation

It's taken me almost 4 hours, but I've attached my EEEBox XP PC, monitor and PSU to my build assembly. No end of axis sensors wired or fitted yet, that can be another day. I have some reasonably heavy MDF attached, and it seems to be moving freely on the M6 and M8 threads. The Y axis still needs to be connected, it's the only floating one. X and Z are fixed motors, and have fixed wiring looms. Z is not yet used.

I have the stepper axis calculations back running on alternate interrupts, as I think excessively high frequency resetting of the PWM was preventing cycle completions from occuring.

It occurred to me today that I could run a "lawn mowing" operation with a router bit and some X & Y stepper excercises, and clean myself a perfectly flat platform if required.

Wednesday, November 4, 2009

Guy Fawkes

Today is the day, that in my youth, we could let off sky rockets, bangers, etc. Now, for my kids, it's only the etc. First rockets were banned, then bangers.
Anyway, before I go and play pyromeister with the kids, this is where I'm up to:

96 servo increments, representing approx 55 degrees movement. (improved resolution)
Each main interrupt, the interrupt:
- Updates the 5 x servos.
- Updates the 5 x PWM channels, 0% to 99.75%
- Checks the steppers: only one is step-updated in any interrupt, 31 interrupts are then serviced before the next motor is checked and so on.

This will be my next target for change, I want to use the granularity of the missed cycles to allow for smooth acceleration and deceleration. Ideally, this needs to be mass adjusted for each axis seperately, and possibly with an allowance for increased weight of additive build, decreased weight of subtractive build, during progress, if full optimisation is needed.

During a long g-code move, it's expected that there will be no acceleration or deceleration for the midsection of the move, here's where I'm going to have to look at some different algorithms. Stopping is achieved by an axis current position equaling a set target location, but I will need to decide somehow, what granularity to use, in creating intermediate locations between start and finish. If the next position is too close to the current one then I would expect slow stepper movement, and if it's far, then I would expect fast movement. I need to try to avoid pixelation type granularity as much as possible, while doing an accurate line, curve etc.

Saturday, October 31, 2009

Back again.

After a long break, during which my mother almost died of a menningoccocal infection, followed by pnumonia, I'm resuming work on my machine. I've been busy modeling small speed boats and jet units the hard way.

I'd put off ordering some low gate drive voltage mosfets, but finally got some from Farnell, soldered them to my PCB, and I've been familiarising myself with the build environment and my SW again... it's been that long !

I've got the 5 servo channels able to swing slightly more than 90 degrees, in 40 steps. I may tweak that later, but I'm controlling most things from one busy interrupt, with stepper drive updates staggered over sequential interrupts, to reduce average interrupt processing time.

Last week, it occured to me that the brushless motors I've been having so much fun with recently in my mini RC jetboats, should also work off my CNC PCB, so I tried one, the brushless ESC reciever connector goes on my board where a servo would plug in, separate power, and it works ! I'm not too surprised, but it opens up a lot of extra, and simple expansion possibilities. Firstly, brushless motors are available from around 10 watts up to around 10KW. They are a three phase motor primarily designed for the RC hobby industry, but the variety available, the efficiency, and the reliability make them very useful in general.

To get one running on my board, I select an off the shelf (from hong kong anyway) speed controller and motor, select my power source, connect up to my board, and I have control !
They are rated on "kv", of which the "k" is a misnomer, for example, a 750kv motor will run approx 750 rpm per volt, i.e. on 12 volts, 9000 rpm.

Dentist drills are now using them... you can get them over 10000kv, i.e. 120,000 rpm
However, the ease of assembly of multi pole motors (like stepper motors) means that for many applications, you don't need gears.

It it feasible to use a brushless RC motor for a screw thread drive ?
I don't think so, not unless you are trying to span a very large distance very rapidly, and don't need precision. The electronic speed controllers often have a "brake" function, that would be useful, but there would be a lag between the servo control signals, and the motor's response. Some of them are pretty good, I have a 3500kv motor outrunner (magnets inside an out-running-bell) that gets up to speed so fast, that it was twisting my first mini jetboat upside down in the air the moment it left the water. That wasn't from torque effect of a prop (It was a custom jet with stator counteracting engine torque), but of the motor accelerating the rotor to full speed in a fraction of a second. However, there will be applications using them, and with encoder feedback, they will do the job in less demanding applications. However, I'm thinking shorter term at the moment, and I think a brushless motor would make a great milling motor.

I'll still be a little slow for a while, and I'm going to ignore my SD card functionality for a while and used either USB serial or normal serial for loading the G-code (when I get that far!)
The "Mass storage device" software is a nasty piece of code that takes over large sections of a micro's OS and C library files, and the ST hardware implementation is... not simple.

Wednesday, July 8, 2009

chicken before egg before chicken before egg before...

I've been a bit quiet on here lately, but I thought it was time for an update.
I could be silent about the difficulties I face, and present the "business is good" smiling face of a salseman, but hey, this is real life, and you have to crack eggs to make the omlette !

Firstly, when I designed the board, I'd intended to run it with MOSFETs for my general purpose power outputs. However, when I looked up the specifications of the MOSFETs I still had a part tube in stock of from some years back, my suspicion was proved right, that their gate drive requirement was too high. For some strange reason, I decided to use darlington transistors, which were pin compatible, but I forgot that the base can sink a lot of current. All went well,until I decided to try ramping the PWM output on a motor that will take around 10 amps, as the ramp speed built up, I overloaded the darlington transistor, and it fed back a nasty spike to my arm microcontroller, and cooked it. :(

At that point, I realised that I hadn't designed in base resistors either, because I didn't need them when driving MOSFETs !

So... I flamed the centre of the chip until I could lift it off.
By this time, my first board was getting a little bit too much action around the fragile 100 pin TQFP package traces, and some were starting to lift off.
My attempt at resoldering a new arm onto the same footprint didn't go particularly well, so I started a new board, while also hunting for my super magnifying goggles, which took a while to surface.

Eventually, I found my goggles, by which time I'd partially assembled a new board.
By the time I'd tidied up my PCB traces and alligned them , improving with each session, I felt like a highly skilled surgeon, only without the Kudos, the nurses to hand me forceps etc, and without any sign on the horizon of even a smidgeon of a surgeon's generous sallary package.

Currently, I have my original board, of which a couple of the stepper motor control traces may or may not work since my last microsurgery, and my new board, which seems to be all good so far.. brand new components, all tested so far, in good working condition.

However, I designed in USB and SD card functionality to my hardware, and it's pretty pointless loading up a coordinate file, or gcode file into flash or the microcontroller to prove my stepper motors work, that's not a deterministic test.

Determinism is the stuff that happens in real life, not on someone's test bench. Determinism, when I read about it many years ago in an excellent book called "The Holographic Paradigm", is basically the theory that if you want to know how something will turn out in real life, the very best simulation requires maximum similarity to the actual situation, an is in fact, tha actual situation itself ! A bit tough for people like weather forecasters, but they do the best they can.

So, I started on merging the USB Virtual com port project with my project.

EEEEK !!!!@$!@# ! ~~~~ incompatible libraries !!!

After a late night edit of some source files to try and achieve a degree of compatibility, when I wasn't at my freshest either, I broke my project.

So, where I'm at now, is I have a working backup prior to the attempted merge, and lots of my own new code which also runs fine when it's got coherent source libraries.

I've decided that the best way to progress now (after going to Jaycar and picking up some more USB printer sockets and SD cards SMD sockets), is to use the USB Mass_Storage sample project, and get that working on my custom hardware, that way, I have the most difficult (to me) part of the whole project running, and then I can take my custom code (which I know), and merge that to the USB Mass Storage project instead.

Until I have the USB code working, I can't test out gcodes sent from my PC,so it's pointless writing the gcode processing routines yet, the way I see it.

Monday, June 15, 2009

After some frustration, I have the smallest amount of progress, and thought I'd post it. Others may have similiar issues.

I've been having issues with the bootloader which can be configured to automatically reset the STM32 chip in flash mode, without the need to change the chip from bootload mode to flash mode and then push the reset button. In my case, a lot of the times after my code changes, the chip doesn't boot from the bootloader, and I have to change to flash mode and reset.

I'm pretty sure that the problem is with the C "linker" that was default for my project, so I've been looking off an on over the last several days for the linker script file, which is supposed to tell the C compiler where the different variables, constants, RAM based and Flash based code should be put within the STM32's 4 GB potential address space.

In my project, there is a default link file enabled, and I searched on it a couple of times, trying to find it so I could check the file contents and settings. Alas, it was reported not found by windows file search program.

Today, I did a more exhaustive manual directory search, and found some of the Raisonance sample projects have a normal link file, and some have a .elf.ld link file. This will be due to the different memory usages ofthe different Raisonance code samples.

I kept looking, and found a generic script file that was almost the same as that in the project defaults, only with the second and third letters of the file name transposed.

Just one small, but infuriating little error. I don't know that I would have the patience to develop on a platform like this if I was younger, and had not had the winning experiences I've had with assembler in 8-bit microcontroller platforms, but I don't loose sight of the promise at the end of this project. The C language itself is not bad, it makes a lot of use of symbols in a tightly packed manner, and so you can end up having an extremely dense piece of code fitting into one line, but then you can end up surrounding it with a { on the preceeding line, and a } on the line following to tidy the look of your code. Weird.

So, I now know where the linker configuration file is, and what it's real name is, I can move it to my project directory and fiddle with it. There's a lot of waffle in it...*

Tuesday, June 9, 2009

How Graham decided to make better Jet units for his RC boats:

This blog is, at the moment ! dedicated to my motherboard design for a 3D materials processing machine.

I started this as a 2009 new year's project, and by the end of January 2009, I made the decision (having built the 3D stage), that I didn't want to buy a soon to be obsoleted circuit board to control it. Having been previously in business for myself as an electronics and software engineer, to proceed, my next step was to design my own circuit board.

This is what I came up with:
You can see at top right, the axis power electronics for 4 x stepper motor control, with 2 coils each, and 2 connections to each coil !
Down the left side, from top to bottom, are:
  • PWM transistor outputs 1 to 5
  • RS485 expansion
  • I2C expansion
  • Keypad



The grey looking square in the middle bottom position is the brain, an ARM Cortex M3 16/32 bit processor. It's great great great great great great great "it" was the acorn archimedes ARM, a much aclaimed microcontroller that was superior to the Intel x86 chips of the day, but not marketed as sucessfully. In interesting trivia, one of the main designers of the chip was "gender reassigned" and became female. Since then, ARM has undergone changes, and is now marketed as IP to big Silicon chip manufacturing companies.
STMicroelectronics, a company that seems to specialise in maximising I/O flexibility of it's product offerings, joined in, in utilising the Arm Cortex M3 core for products of it's own fairly early on, and I'm using their STM32F103VBT for my circuitboard.

In addition to the features I listed above, I also implemented these:
2 x position encoder channels (each channel uses two sensors)
2 x dedicated analogue voltage inputs, intended for temperature monitoring.
1 x Piezo with direct drive. You can actually play tunes on the stepper motors, but it's slightly more tricky to do if you don't want the stepper motors to actually move out of position !
5 x Servo control outputs, also configurable for other purposes if enabled as such in the software.
1 x LCD connector, for common 4 wire data mode.
1 x SD Card socket, for stand alone 3D model building operation.
1 x RS232 connection for loading the firmware, and available for debugging, diagnostics, or reporting purposes.
1 x RS485 connection for slave devices, or daisy chaining more of the same.
Anyway, those were the goals !

I designed to use the L298 chip, which is good for 2 amps continous. I decided to do that, because it handles the majority of small stepper motor control applications, and in that way, increases the potential volume traded of standard type circuitboards. That helps on both standardisation, and cost.

Most people use a decoder chip, like the L297 to interface between the brain on the circuitboard (the microcontroller or uC for short), and the power output hardware (the L298), but in my case, I decided to control the L298 directly, which allows for some tricks, I can potentially send wave forms via PWM to the stepper motors for smoother movement, and with sub steps inside what would otherwise be available.

The picture above was just the "artist's impression", generated by KiCad as a 3D view of the known components 3D shapes.

Anyway, I completed the design, and sent the plans to PCBCART in Hong Kong.
A couple of weeks later (I used the no-hurry-schedule ordering option), I got fifteen circuitboards from them:

It took me a couple of weeks to get all the components together to make the first one, and this is what it looked like:

You can see it at the right, perched on the EEEBOX that I bought for it, as a Windos server.

I use Linux otherwise, but it's quite messy getting started with ARM C programming, and so I used a better known environment. The EEEPC is low powered as Intel computers go, it uses an Atom processor, and isn't much good for keeping hands warm on cold winter nights.


Next was software !
I got the stepper motors running after taking some time to learn C (I used to use assembler only, on the embedded microcontroller end), and some battles to get the tool chain doing what I wanted it to. Pulse width modulating the steppers was second, and then applying the PWM to the coils independently in a wave form. I have that now, but at the moment only as a crude 1/2 steps between the 4 full power positions.

Next, (and up to date progress), was the LCD !
I got that working tonight, the picture's a bit dark, but you can see it on the bottom right hand side:

End of the day's post !