July 6th, 2014 | Tags: , , , ,

Playing around with Arduino finally implemented the printf. The
floating point library can be only enabled by modifying the IDE Utilizar float con sprintf() y derivados en Arduino.

/* simple implementation of printf for SoftwareSerial */

#include <SoftwareSerial.h>
#include <inttypes.h>

class mySerial : public SoftwareSerial {

  public:
    mySerial(uint8_t receivePin, uint8_t transmitPin, bool inverse_logic = false) :
      SoftwareSerial(receivePin, transmitPin,inverse_logic) {}

    virtual size_t write(uint8_t byte) {
      return SoftwareSerial::write(byte);
    }

    int printf(char* fmt, ...) {
      char buff[256];
      va_list args;
      va_start(args, fmt);
      int return_status = vsnprintf(buff, sizeof(buff), fmt, args);
      va_end(args);
      uint8_t *s = (uint8_t *)&buff;
      while (*s) write(*s++);
      return return_status;
    }

};

mySerial m(PD0,PD1);

/* to enable support for floating point functionality,
   use following linker switches
   -Wl,-u,-lprintf_flt vfprintf
*/   

void setup() {
  m.begin(9600);
  m.print("Hello from Arduino!\n");
  m.printf("%s %.3f %x %d %4o\n", "Hello", 3.14159, 0x80, 333, 128);
  m.printf("%16s %08x %e\n", "Hello", 0x1234, 1e-10);

  printf("\n\n");
  printf("%.3f %en", 3.14159, 3.14159);

}

void loop() {
}


I started a long awaiting project, to build a Geiger-Müller radiation counter. The Geiger tube is a SBT-11 russian tube for alpha, beta and gamma radiation. The tube is quite sensitive and of a relatively small size. The picture at the right hand side shows the SBT-11 tube and the high voltage power supply in a plastic CCFL case. The power supply works with 3.3V. A small CCFL transformer boosts the 3.3V to about 390V. The switching regulartor IC is a MC34063.

The datasheet says the tube has 0.6 pulses/sec of own background. 0.6 pulses/s are about 36 Pulses/min. To get the prove I started to count the pulses.

The Measurement

The common method to measure pulses is a round robin array to save the pulses and the sum of pulses yelds the CPM.
The code below shows an Arduino example:

ISR(each_second) {
   int pulses_per_second = count - last_count;
   register unsigned int cpm_pos = it_cpm++ % 60;
   cpm[cpm_pos] = pulses_per_second;

   int sum_cpm = 0;
   for(int i=0;i < 60;i++)
      sum_cpm = sum_cpm + cpm[i];
   Serial.println(sum_cpm, DEC);
}

The Result


The diagram on the left hand side shows the histogram of about 20 hours measurement. The own background of the tube has an intervall of 0 to about 86 pulses per minute. It shows (as expected) a discrete normal distribution with a mean of 36-38 pulses per minute or 0.6-0.63 pulses per second. So what does it say? This may concern everybody who needs to measure low radiation or background radiation. Usually it is not needed to substract the 0.6 pulses from result, because it is more expressive to give an confidence interval as an result.

ARMstrap eagle PCB

What?

ARMstrap Eagle is an very nice OpenSource development board with a ARM Cortex-M4 STM32F4[012]7 CPU running at 168 MHz. The main feature of this board is the Black Magic Probe embedded debug interface. Beside of this it is interesting for me to learn how other features like the true Random Generator, AES encryption, RTC and so on work.

Why?

Since the ARMstrap Eagle documentation is not very chatty about on how to get everything done on Linux, here are additional important notes:

Build Environment

A popular repository is GNU Tools for ARM Embedded Processors.

  • Extract the files to your desired directory i.e. /opt or ${eclipse_home}.
  • Modify your PATH environment variable:
     echo 'export PATH=/opt/gcc-arm-none-eabi-4_8-2014q1/bin:"$PATH"' >> ~/.bashrc

UDEV Settings

ARMstrap eagle uses the Vendor-ID from OpenMoko:

~$ lsusb
Bus 004 Device 018: ID 1d50:6018 OpenMoko, Inc.
Bus 004 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub

Here are my settings:

# /etc/udev/rules.d/55-armstrap.rules
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1d50", ATTRS{idProduct}=="6018", RUN+="/sbin/modprobe cdc-acm", GROUP="plugdev", MODE="0660", SYMLINK+="eagle%n"

After you create the 55-armstrap.rules, you need to reload your rules

 udevadm control --reload

The udev devices will finally appear as:

# ls -l /dev/eagle*
lrwxrwxrwx 1 root root  7 May 16 19:03 /dev/eagle1 -> ttyACM1
lrwxrwxrwx 1 root root  7 May 16 19:03 /dev/eagle2 -> ttyACM2
lrwxrwxrwx 1 root root 15 May 16 19:03 /dev/eagle4 -> bus/usb/004/019

and

# for n in /dev/eagle*; do ls -l /dev/$(readlink $n); done
crw-rw-r-- 1 root plugdev 189, 1 May 16 19:03 /dev/ttyACM1
crw-rw-r-- 1 root plugdev 189, 2 May 16 19:03 /dev/ttyACM2
crw-rw-r--+ 1 root plugdev 189, 402 May 16 19:03 /dev/bus/usb/004/019

You may also take a look at the README of the Black Magic Debugger.

Eclipse Settings

The new GCC 4.8 needs to have some different settings in Project->Properties->C/C++-Build->Settings

Cross GCC Assembler->General

 -mcpu=cortex-m4 -mthumb -mno-warn-deprecated -mfloat-abi=hard

Cross G++ Linker->Miscellaneous

 -mcpu=cortex-m4 -mthumb -mno-warn-deprecated -mfloat-abi=hard

Cross GCC Compiler->Miscellaneous

 -c -fmessage-length=0 -march=armv7e-m -mcpu=cortex-m4 -fno-common -mthumb -mfloat-abi=hard -mfpu=fpv4-sp-d16 -MD -ffunction-sections -fno-builtin 

Cross GCC Compiler->Debugging

 -g3 -ggdb

An important step -ggdb. Without it you wont see any source int the debugger.

GDB Hardware Debugging

Rename the first line to:

target extended-remote /dev/eagle1

Serial Console

I belive /dev/eagle2 is the serial console. I need to check this.

Flashing/Uploading the Code

The debugging configuration flashes already and starts debugging.
To have only only flashing without debugging I created a small script

# /path/gdbupload.cmd
set print pretty
set auto-load safe-path /
target extended-remote /dev/eagle1
mon swdp_scan
attach 1
load
detach
quit

In eclipse select Project->Properties and got to:

C/C++-Build->Settings

select Configuration->Release
In Post-build steps->Command insert

arm-none-eabi-gdb -batch -x /opt/armstrap/gdbupload.cmd ${ProjName}.elf

The output for relase build

includes/STM32F4xx_StdPeriph_Driver/src/stm32f4xx_adc.o includes/STM32F4xx_StdPeriph_Driver/src/misc.o
arm-none-eabi-gdb -batch -x /opt/armstrap/gdbupload.cmd blinky.elf
Target voltage: 4.9V
Available Targets:
No. Att Driver
 1      STM32F4xx
0x08000366 in loop ()
Loading section .isr_vector, size 0x188 lma 0x8000000
Loading section .text, size 0x3a0 lma 0x8000188
Start address 0x8000288, load size 1320
Transfer rate: 3 KB/sec, 660 bytes/write.
Detaching from program: /opt/armstrap/workspace/blinky/Debug/blinky.elf, Remote target

19:29:02 Build Finished (took 513ms)

April 27th, 2014 | Tags:

Today I’ve been able to properly convert a tiff file to pdf and
then back to tiffg3. The commands are:

$ convert -page A4 -density 600 -quality 100 -compress Zip file.tiff file.pdf

It is important to set the pagesize here, otherwise GhostScript wont resize it properly.

gs -q -dBATCH -dNOPAUSE -dSAFER \
        -sPAPERSIZE=a4 -dNOPAGEPROMPT \
        -dFIXEDMEDIA -sDEVICE=tiffg3 \
        -r204x196 -sDithering=gsmono -dPDFFitPage
        -sOutputFile=file-g3.tiff file.pdf

Important here also the -dPDFFitPage

January 9th, 2014 | Tags: , , , , , , ,

The router’s default IP is 192.168.1.1. To easily access the router, I first added an alias with the IP of the router’s subnet:

# ifconfig eth0:0 192.168.1.2

# route
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
192.168.1.0     *               255.255.255.0   U     0      0        0 eth0
192.168.0.0     *               255.255.255.0   U     0      0        0 eth0

# ping 192.168.1.1
PING wrt (192.168.1.1) 56(84) bytes of data.
64 bytes from wrt (192.168.1.1): icmp_seq=1 ttl=64 time=0.345 ms
64 bytes from wrt (192.168.1.1): icmp_seq=2 ttl=64 time=0.933 ms
^C
# nc -z -v 192.168.1.1 80
wrt [192.168.1.1] 80 (http) open

Now it’s eays to connect the router’s web interface and change it’s IP as needed.

If you have chinese firmware, then use this menu entry to upload new firmware:

More information you’ll find on the OpenWRT pages: Flashing

Office phones have to be online at office hours, otherwise a voicemail should be enabled. They should also be aware of holidays.

The dialplan

; extensions.conf
exten => 1234567,n,GotoIfTime(09:00-18:00,mon-fri,*,*?hcheck:vm)
exten => 1234567,n,GotoIfTime(09:00-14:00,sat,*,*?hcheck:vm)
exten => 1234567,n(hcheck),AGI(isholiday.pl)
exten => 1234567,n,GotoIf($[${ISHOLIDAY} = "YES"]?vm)
exten => 1234567,n(open),NoOp
...
exten => 1234567,n(vm),VoiceMail(1234567,sub)
...

A little perl-script checks for german holidays. The AGI figures out the holiday days for each year, so no updates are needed except a new day was added or removed. The AGI:

#!/usr/bin/perl
# holiday check for asterisk
# /var/lib/asterisk/agi-bin/isholiday.pl

use strict;
my ($isholiday, $today,$ymd);

END { printf "SET VARIABLE ISHOLIDAY %s\n\n", ($isholiday)?"YES":"NO"; }

while(<STDIN>) {
     chomp;
     last unless length($_);
}

use Date::Holidays::DE qw(holidays);

my $feiertage_ref = holidays(
    WHERE    => [ 'common', 'ni'], # ni = Niedersachsen
    FORMAT   => "%F",
    YEAR     => 1900 + (localtime())[5],
    ADD      => [ 'heil', 'wei1', 'wei2',
                  'osts', 'ostm', 'pfis',
                  'pfim', '3okt', 'silv',
                  'mari' ]);

my (@ymd) = (localtime)[5,4,3];
$today = sprintf "%s-%s-%s", 1900+$ymd[0], 1+$ymd[1], $ymd[2];

for my $d (@$feiertage_ref) {
    if ($d eq $today) {
        $isholiday = 1;
        last;
    }
}
December 15th, 2012 | Tags: , , , , , ,

There is often a need to debug scripts which are started by daemons, so you have no input/output available. The following snippet easily redirects stdout and stderr to a file:

#!/bin/bash

exec >> /tmp/script_debug.log 2>&1
set -x 

echo Start: $(date)

: buggy code

echo Stop: $(date)

and here the output:

$ cat /tmp/script_debug.log
++ date
+ echo Start: Sat Dec 15 08:37:45 CET 2012
Start: Sat Dec 15 08:37:45 CET 2012
+ your-buggy-cmd
foo: line 8: your-buggy-cmd: command not found
++ date
+ echo Stop: Sat Dec 15 08:37:45 CET 2012
Stop: Sat Dec 15 08:37:45 CET 2012
November 12th, 2011 | Tags: , ,

The first part of Parallel Bash dealt with creation of parallel processes, so now it’s time for a real parallel tool.

The Apache benchmark tool ab has the disadvantage of sending only one URL for requests. To emulate a real server load we need some tools which can download several different files (.jpg, .js, .php, .css, ..) where each of them causes different CPU loads and network througphut, as well as different sizes of tranfered data. This can easily be done with httrack or wget.

And here is how:

The parallel routine pwork runs a site-mirror and collects the elapsed time in a log file

...
HTLOG=/tmp/httime.$$.log

pwork () {
    TMPDIR=$(mktemp -d /tmp/htbench_instance_XXXXX)
    TMPFILE=$(mktemp /tmp/htbench_log_XXXX)
    ( cd $TMPDIR
      #  append elapsed time to HTLOG
      /usr/bin/time -f "%e" -o $TMPFILE
      httrack -c8 --mirror --depth=2 -Q -q $1
      if lockfile -1 -r12 $HTLOCK; then
          cat $TMPFILE >> $HTLOG
      fi
      rm -f $HTLOCK $TMPFILE
    )
    rm -rf "$TMPDIR"
}
...

Limit the benchmark to n loops:

...
while [ $COUNT != 0 ]
do      J=$(jobs -p)
        echo "jobs left: "$COUNT
        N=$(echo $J|wc -w)
        if [ -z "$N" -o "$N" -lt $PARALLEL ]; then
            pwork "$URI" &
            (( COUNT-- ))
        fi
        sleep .2
done

Show final results:

...
show_results () {

    MINRUN=$(sort -n $HTLOG|head -1|cut -d' ' -f1)
    MAXRUN=$(sort -n $HTLOG|tail -1|cut -d' ' -f1)
    AVGRUN=$(perl -e '$sum=$count=0;
                         while (<>) {
                             chomp;$sum+=$_;$count++; }
                          printf "%.2fn", $sum/$count;' $HTLOG)
    rm $HTLOG

    echo "Benchmark Results"
    echo "================="
    echo
    echo "longest runtime:  "$MAXRUN
    echo "shortest runtime: "$MINRUN
    echo "average runtime:  "$AVGRUN
    echo
}

reaper () {
        echo "waiting to finish $RUNNING" >&2
        wait
        show_results
        exit 0
}

trap reaper 0 1 2 3 11 15
...


Use with care!

Download latest version:
htbench.sh

August 21st, 2011 | Tags: , , , ,

There is often the need to run several bash scripts in parallel. To achieve this, one need to keep track of the running processes. Here’s my solution:

#!/bin/bash

# parallel child processes
PP=5

if [ -n "$1" ]; then
        sleep $1
        exit
fi

reaper () {
        echo "waiting to finish" >&2
        wait
        exit 0
}
trap reaper 0 1 2 3 11 15

while :;
do      J=$(jobs -p)
        echo "running: "$J
        N=$(echo $J|wc -w)
        if [ -z "$N" -o "$N" -lt $PP ]; then
            $0 $[ $RANDOM % 8 ] &
        fi

        sleep .2
done

Paste this snippet to a file, and set the executable flag.

$ cat > parallel.sh
$ chmod +x parallel.sh

The output will look like this:

$ ./parallel.sh
running:
running: 25431
running: 25431 25438
running: 25431 25438 25445
running: 25431 25438 25445 25452
running: 25438 25445 25452 25459
running: 25445 25459 25466
running: 25445 25459 25466 25473
running: 25445 25459 25466 25480
running: 25445 25459 25466 25480 25487
running: 25459 25466 25480 25487
running: 25459 25466 25480 25487 25499
running: 25459 25466 25487 25499
running: 25459 25466 25487 25499 25511
running: 25466 25487 25499 25511
running: 25466 25487 25499 25511 25524
running: 25466 25487 25499 25511 25524
running: 25466 25487 25499 25524
running: 25487 25499 25524 25541
running: 25487 25499 25524 25541 25548
running: 25487 25524 25541 25548
running: 25524 25541 25560
running: 25524 25560 25567
running: 25524 25560 25567 25574
running: 25560 25567 25581
running: 25560 25567 25581 25588
running: 25560 25567 25581 25588 25595
^Cwaiting to finish
waiting to finish
$

Comments are welcome.

See also a similar solution of Grumbel: Parallel Bash

TOP