Jump to content

mpymike

Members
  • Content Count

    46
  • Joined

  • Last visited

  • Days Won

    1

Posts posted by mpymike


  1. For me the motivation for using Python is that it is an easier language to introduce to kids.

     

    A full Python implementation is a higher level more sophisticated language, has higher level constructs, more abstraction is possible,

    more compact code, easier to understand, easier to maintain, faster development time. (ie the usual arguments between language benefits)

     

    I would not claim that the Python implementation would be any more efficient, in memory or performance.

     

    Looked at Lua some time back, I like the language a lot, and probably a better language for a uC than Python

    but for kids (and me) the aim is using the same language for the uC and regular software.


  2. Thanks t0mpr1c3, interesting reading, I shall keep an eye on how uJava progresses.

    First thoughts, the memory footprint does look smaller than MicroPython, which could be

    due to many reasons.

     

     

    Well, I would agree that cut-throat competition among the various ARM vendors has resulted in some truly amazing price points....

     

    We are practically at the point where 60 - 80 kB of overheard is no big deal even if you only want to blink an LED.

     

    Remind me again about why there is any point in using the MSP430 in this day and age?

     

    My original motivation for using the 430 Launchpads:   

    1) The price - when it was $4.30

    2) Simple architecture that is easy to understand and explain.

    3) DIL component that can be plugged into a breadboard, making it more useful for building electronic projects.

      

    Now however the ARM products are ubiquitous...

    Anyone know of a standalone ARM uC in a DIL package?

     


  3. @@t0mpr1c3   I think it depends on the size of the bytecode VM. As I remember, Forth is fairly simple and can fit onto a small uC. But I wasn't aware of any Java VM that can fit onto a small uC. If anyone knows of one I'd like to look at it. May even be suitable for

    Jython. (which is Python running on a Java VM) 

     

    @@rockets4kids The source is not released yet, but from his kickstarter page he describes it as:

     

    Micro Python has the following features:

    • Full implementation of the Python 3 grammar (but not yet all of Python's standard libraries).
    • Implements a lexer, parser, compiler, virtual machine and runtime.
    • Can execute files, and also has a command line interface (a read-evaluate-print-loop, or REPL).
    • Python code is compiled to a compressed byte code that runs on the built-in virtual machine.
    • Memory usage is minimised by storing objects in efficient ways.  Integers that fit in 31-bits do not allocate an object on the heap, and so require memory only on the stack.
    • Using Python decorators, functions can be optionally compiled to native machine code, which takes more memory but runs around 2 times faster than byte code.  Such functions still implement the complete Python language.
    • A function can also be optionally compiled to use native machine integers as numbers, instead of Python objects.  Such code runs at close to the speed of an equivalent C function, and can still be called from Python, and can still call Python.  These functions can be used to perform time-critical procedures, such as interrupts.
    • An implementation of inline assembler allows complete access to the underlying machine.  Inline assembler functions can be called from Python as though they were a normal function.
    • Memory is managed using a simple and fast mark-sweep garbage collector.  It takes less than 4ms to perform a full collection.  A lot of functions can be written to use no heap memory at all and therefore require no garbage collection.?
    The only other source of info I know of is comments page 

  4. MicroPython is a pretty full python implementation of the language.

    Setting aside the large memory footprint overhead, the main

    issue will be that it will lack all the libraries and especially the

    hardware libraries (at least initially)  It will have a long way to

    go to catchup with the extensive  Arduino/Energia selection. 

     

    IMO describing  Python as a scripting language is a bit meaningless.

    More relevant is the fact that most python implementations including

    MicroPython are byte code interpreted. The virtual machine is running

    on the microcontroller. That must account for a hefty chunk of the overhead.


  5. I had to go for it! I signed up for one of the MicroPython boards. Really like the

    small breadboard friendly footprint and SD socket.

     

    For me the beauty of Python is that it is compact, readable, intuitive, and easy to learn. 

    There are free libraries for just about everything.  IMO using python is the quickest way of

    developing software. So porting it to microcontrollers is the holy grail.

     

    It is a shame that Python requires such a large memory footprint to run, putting it out of reach for the

    modest msp430s.

     

    With the MicroPython project the author has completely rewritten Python optimizing it for microcontroller

    use, specifically reducing the memory footprint.   Even after doing this, his barebones print('hello world')

    example comes out to whopping 60k flash and 4k ram.  My guess MicroPython will be suitable for

    microcontrollers with >256k  flash and >32k ram. 

     

    My own attempt at a python implementation (mpy) manages to get into an msp430, but only by throwing out most of

    the python language leaving just enough to do the simple stuff. 


  6. Thankyou everyone! I had a whole lot of fun doing this project.

     

    Halloween evening started out really well, I also brought out the mpy creeper and zombie models

    and programmed up some other Launchpads with flashing led displays. There was a lot going on.

     

    However my poor ghost was so busy shuddering and rushing up and down the garden

    that by about 8:00pm the motor started straining for some reason, and then the string snapped   :crazy:  

     

    I think part of the problem was the ultrasonic detector started triggering sporadically. 

    So at the end it was triggering and constantly on the go.

    I suspect that the ghost battery must of drained and the HC-SR04 started to output bad echo

    signals (I forgot to put fresh batteries in it, I think).

     

    Has anyone had good experience using the cheap HC-SR04 ultrasonic detectors?

     

    -mpymike


  7. MPY Halloween Ghost Project

     

    This project is a scary ghost for halloween. It is setup in the front garden to scare away the hordes of trick-or-treaters.
    When a passing trick-or-treater approaches the ghost will scream and move back and forth along side the garden path.

     

    Go to the projects page for more details

     

    http://forum.43oh.com/topic/4524-mpy-halloween-ghost-project/

     

    Also see the video: 
     

    http://youtu.be/80EAMJM0L7k


  8. MPY Halloween Ghost Project
     
    This project is a scary ghost for halloween. It is setup in the front garden to scare away the hordes of trick-or-treaters.
    When a passing trick-or-treater approaches the ghost will scream and move back and forth along side the garden path.
     
    It uses two MSP430s, One for the Ghost to detect passing trick-or-treaters and a second MSP430 to pull the Ghost on a loop of string. See it in action in the video.
     
     


     
     
    The Ghost
     
    The msp430 in the ghost is mounted onto a breadboard with a battery pack stuck to the back.
    An HC-SR04 ultrasonic detector is used to detect objects between 5-8 feet away. The sound comes from a 1.5" 100 ohm speaker from pololu.com and a random flashing high intensity LED are used to frighten away anyone who approaches too close.
     
    I used a low cost 433MHz RF TX module from elecrow.com to send a signal to the pully motor controller. This worked very well it had plenty of range once I added a 12" length of wire as an antenna.
     
    post-3-0-37873600-1382978131_thumb.jpg
     
    The circuit is pretty simple. I used a 4.5v battery pack and a diode to drop the supply for the MSP430 to a safer level. The TX module and the ultrasonic detector needed the higher supply voltage.  I found the HC-SR04 ultrasonic detector to be quite difficult to use. It had a lot of dead positions where it would not detect reliably, (could probably be caused by multipath reflections giving false echos). I had to
    make the code detect echos that were within a narrow range.
    The speaker is driven directly from the MSP430 timer output. Frequency being controlled by the timer period and the volume controlled by the pulse width. 
     

    post-16401-0-94589300-1382996531_thumb.png

     
    The circuit is mounted onto a breadboard. The ultrasonic module was a bit floppy and needs to be held in place firmly as the whole thing gets shaken around quite a bit. it isn't very permanent, but hopefully I will still be able to use it next halloween.
     

    post-16401-0-01783400-1382996552_thumb.png
     
    The program is written in MPY (a simplified variant of Python), and the syntax should be easy enough to understand.


    ######################################################################
    #
    # ghost_screamer.mpy  
    # 
    # ~~~~  Scary Halloween Ghost  ~~~~ 
    # Uses an Ultrasonic Detector on P1_5/P1_4 to detect 
    # presence of passing trick-or-treaters. When detected
    # it flashes LED (P1_0) randomly, makes a whooooh sound and
    # sends a pulse to the Tx module
    # The ultrasonic detector produces a variable width
    # pulse (ECHO on P1_5) whose pulse width is proportional
    # to the distance. Pulses that are too long or to short
    # are ignored as these a false triggers. This was done
    # as the ultrasonic detector HC-SR04 is prone to produce 
    # rogue pulses.  
    # ( Mike Asker 18-Sep-2013 www.mpyprojects.com)
    # 
    ######################################################################
    
    TRIG = P1_4
    ECHO = P1_5
    TX   = P1_3
    SPKR = P1_6
    LED  = P1_0
     
    ######################################################################
    def timer():
        '''Define a timer function. This will be run every 6ms as a watchdog timer interrupt
        This will handle any things we want to do in the background.
        Like sending TX data and flashing the LED'''
        
        global tcount
        global r
        tcount += 1
        
        # Toggle the data signal to the TX module 
        # (I think it needs to be kept modulated for the RX receiver to work.
        # Change the TX pulse form 1ms to 2ms if we want to send a '1' (this is a very 
        # low rate signal!) This is being done once every timer tick (6ms)
        out(TX,1)
        if enable_tx > 0:
            wait(2)
        else:
            wait(1)
        out(TX,0)
        
        # Flash the LED
        if tcount % 10 == 0:
            tcount = 0
            # If the volume is turned on, (ie we have detection)
            # flash the Led in a random manner
            r = random(r)
            if r > 10000 and volume > 0:
                out(LED,1)
            else:
                out(LED,0)
                
    
        
    ####################################################################
    # Main program starts here
    ####################################################################
    
    # Setup the pin directions
    pindir(LED,OUT)     
    pindir(SPKR,PULSEOUT)
    pindir(TRIG,OUT)
    pindir(ECHO,IN)
    pindir(TX,OUT)
    
    volume = 10
    tone = 900
    tcount = 0
    volume_inc = 1
    tone_inc   = 5
    
    
    interrupt_setup( WATCHDOG_TIMER, WDT_ADLY_1_9, timer)  # setup an interval timer 6ms
    eint()                                                 # start the interupt timer running
    pulse_enable(0)                                        # enable the timer0 used for the speaker
    
    # Enter a continuous loop
    while 1:
        
            # Output a trigger pulse to start the ultrasonic detector
            out(TRIG,1)
            wait_cycles(50)
            out(TRIG,0)
    
            # Wait a millisecond before we start to look for the echo
            # this gives enough time for the ECHO signal to go high
            # at the start of the pulse        
            wait(1)
            ecount=0
            echo = 0
            
            # While the ECHO signal is high loop round once every 10us
            # and increment ecount. Break out of the loop when echo
            # goes low, the value of ecount will be the pulse width
            # (units of 10us) 
            while ecount < 200:
                if echo == 0 and inp(ECHO) == 0:
                    echo = ecount
                ecount += 1
                wait_cycles(10)
    
            # If the width is within the narrow range of 400us - 600us
            # then we have detected a trick-or-treater        
            if echo > 40 and echo < 60:
                
                # Send a '1' to the RF module
                enable_tx = 1
                
                # Make a whoooh sound!
                tone = 900              # Set an initial tone frequency value
                tone_inc   = 10         # Start with an initial +ve tone increment
                for i in range(5):      # Repeat the whoooh 5 times
                    for j in range(20):
                        # Increment the tone frequency to make the spooky whooo sound
                        # but only within narrow limits. When it hits a limit change
                        # the direction of the increment, so the tone will go up and then
                        # down
                        tone += tone_inc              
                        if tone > 1100 or tone < 800:  # if the tone hits the limits invert the increment   
                            tone_inc = -tone_inc
                        volume = tone/2          # Set max volume to max by making the width half the period
                        pulse_period(0,tone)
                        pulse_width(0,volume)
                        wait(50)                 # update the tone once every 50ms
                    enable_tx = 0                
                    # Switch off the TX module after the first whooo
                    # because we need to give only a short pulse to the RX module
                    # otherwise it will keep running  
    
            #switch off the speaker after we are finished with the whooo by setting the volume value to 0
            volume = 0
            pulse_width(0,volume)
            wait(100) 
            
           
                
        
    
    

     
    The Pully Motor Controller
     
    This is mounted onto a piece of hardwood attached to the house by the front door.
     
    post-3-0-13640800-1382977959_thumb.jpg
     
    It contains a pully driven by a 12v gear motor. I upped the voltage to 17v as I wanted more power from it!
    I used an old 17v laptop supply as it could supply plenty of current.
     
    The motor controller was a low cost L298N module I got from Aliexpress. This was able to handle the current and the higher operating voltage.
     
    I mounted a Launchpad board. Any of the normal DIL MSP430 chips can be used as the code only takes 1800 bytes of flash.
     
    There are two pushbutton switches to allow the motor to be manually controlled while I was working on it.
    There are two infrared detectors to detect when the ghost has reached the end of its travel, both to the left and to the right. I got the infrared detectors from buildsmarterrobots.com, but I don't think he is selling them anymore.(other detectors can be used instead).

     post-3-0-49063000-1382977923_thumb.png

    The circuit uses a 3.3v regulator for the Launchpad MSP430 supply and for the infrared detectors. I needed to add a 33ohm power resistor to this regulator to reduce the power the regulator was dissipating as the drop from17v to 3.3v together with the rather large current taken by the infrared detectors meant the poor regulator was getting too hot. By adding this resistor it reduced the voltage drop across the regulator, and so lowering its power dissipation.  The L298N motor controller and the RF Receiver use a 5v supply, I used a 5.1v zener diode for this supply (I would of used a 5v regulator, if I had one)

     

    post-3-0-59238600-1382978005_thumb.jpg
     
    Here's the MPY code for the ghost pully controller
     

    ######################################################################
    #
    # ghost_chaser.mpy  
    # 
    # Program to move a ghost along a line
    # ( Mike Asker 18-Sep-2013 www.mpyprojects.com)
    # 
    ######################################################################
    
    SWLEFT  = P2_7
    SWRIGHT = P2_6
    
    MOTOR_A1IN = P1_0  # also the Red LED     >> MOTOR RIGHT 
    MOTOR_A2IN = P1_6   # also the Green LED   >> MOTOR LEFT
    
    RX    = P1_5 
    RXLED = P1_4
    
    IRLED = P1_2
    IRTOP = P1_7
    IRBOT = P1_3
    
    STOP   = 3   
    LEFT   = 1
    RIGHT  = 2
    MIDDLE = 0 
    
    #########################################
    def left():
        global motor
        out( MOTOR_A1IN, 1)
        out( MOTOR_A2IN, 0)
        motor = LEFT
        out(IRLED, 1)
    
    #########################################    
    def right():
        global motor
        out( MOTOR_A1IN, 0)
        out( MOTOR_A2IN, 1)
        motor = RIGHT
        out(IRLED, 1)
        
    ##########################################    
    def stop():
        global motor
        out( MOTOR_A1IN, 0)
        out( MOTOR_A2IN, 0)
        motor = STOP
        out(IRLED, 0)
    
    ##########################################
    def ghost_dance():
        '''Pull the ghost back and forth a few times
        and then pull it all the way to the door (right)
        wait a while and then pull it all the way
        back to the front gate (left)'''
        
        global position
        position = MIDDLE
        wait(5000)
        right()
        wait(1000)
        for i in range(3):
            left()
            wait(300)
            right()
            wait(300)
        
        stop();   wait(2000)
        right();  wait(3000)
        stop();   wait(5000)
        left()
        
        
        while position == MIDDLE:
            if motor == LEFT and inp(IRTOP) == 0:
               stop()
               position = LEFT
        
        wait(5000)
        stop()
    
    #############################################################
    ## Main program starts here ##
    #############################################################
    
    # Set the pin direction of all the IO pins
    pindir(IRLED, OUT)
    pindir(IRTOP, IN)
    pindir(IRBOT, IN)
    
    pindir(SWLEFT,  INPU)
    pindir(SWRIGHT, INPU)
    pindir(S2, INPU)
    pindir(MOTOR_A1IN, OUT)
    pindir(MOTOR_A2IN, OUT)
    pindir(RX, IN)
    pindir(RXLED, OUT)
    
    out(RXLED, 0)
    position = MIDDLE
    out(IRLED, 0)
    stop()
    
    print( 'prog started' )
    
    rx_count = 0
    lcount = 0
    c0 = 0
    c1 = 0
    rx = 0
    rx_prev = 0
    detect = 0
    
    wait(3000)    # leave some time to allow the supplies to settle.
    
    while 1:    
    
       # If the ghost is moving out (left) and the top ir sensor is activated 
       # then we've hit the endstop, swtich off the motor
       if motor == LEFT and (inp(IRTOP) == 0 or inp(IRBOT) == 0) and inp(SWLEFT) == 1:
           stop()
           position = LEFT
    
       # If the ghost is moving inwards (right) and the bottom ir sensor is activated 
       # then we've hit the endstop, swtich off the motor
       if motor == RIGHT and (inp(IRBOT) == 0 or inp(IRTOP) == 0 ) and inp(SWRIGHT) == 1:
           stop()
           position = RIGHT
    
                  
       # Make the ghost run under button control
       if inp(SWRIGHT) == 0:
           right()
           position = MIDDLE
           
       else:
           if inp(SWLEFT) == 0:
               left()       
               position = MIDDLE
    
       # Stop the motor if the opposite button is pressed while
       # while running
       if inp(SWRIGHT) == 0 and motor == LEFT:
           stop()
           wait(1000)
       if inp(SWLEFT) == 0 and motor == RIGHT:
           stop()
           wait(1000)
        
        
       # Look for an RX signal from the Ghost which indicates that the
       # tick-or-treater has been detected. If detected then make
       # the ghost do a little dance
       rx = inp(RX)
       c0 = 0 
       c1 = 0
       
       # First make sure the motor is already stopped,
       # then if the we have a falling edge on the RX signal
       # count how long it stays low (c0),
       # and then count how long it stays high (c1)
       if motor == STOP and rx_prev == 1 and rx == 0:    
           while inp(RX) == 0:
               c0 += 1  
           while inp(RX) == 1:
               c1 += 1
       
    
           out(RXLED,0)
           # Save the c1 high count, and if it is the within the correct limits
           # then we have a '1' and we have detected the trick-or-treater, lets dance!
           rx_count = c1
           if rx_count > 150 and rx_count < 220:
               detect = 1
               out(RXLED, 1)     # switch on the detection LED 
               ghost_dance()
           else:
               detect = 0
               out(RXLED, 0)
                     
    
       lcount += 1
       rx_prev = rx
    
    

  9. Yeah

     

    Its a ghost suspended on a loop of string running from front gate to front door.

     

    Launchpad #1 mounted in the ghost detects trick-or-treaters (ping detector)

    Flashes LEDs, screams through a speaker, sends signal (RF Tx module)

     

    Launchpad #2 receives signal (RF Rx module) and switches on the motor 

    which pulls the ghost on the string towards the front door along side the trick-or-treaters

    They freak out and run away never to be seen again.

     

    Still waiting for my rf modules from elecrow.com though


  10. I played around with the response time and the min sensor frequency settings but neither helped very much.

    All my testing was indoors so I was surrounded by 60Hz mains interference, and I made no attempt

    to shield the coil.

     

    The datasheet doesn't explain in detail how the Proximity value is calculated, but I suspect that

    the loop gain of the oscillator is controlled by the Rp_min and Rp_max register values.

     

    My guess is that during operation the loop gain is alternately set by the Rp_min and Rp_max values.

    When the LC tank is driven with Rp_min the amplitude of oscillation will grow in amplitude

    until it reaches the threshold voltage, this is the LDC Configuration Amplitude setting (4v). It then

    switches to use the Rp_max  value and the amplitude of oscillation starts

    to reduce until the amplitude crosses the lower threshold. This cycle continues switching

    between lower and upper thresholds. The time it takes for the oscillation to grow or decay

    depends respectively on how close the Rp of the LC tank is to Rp_min and Rp_max values.  

    The ratio of Rp_max time to Rp_min time  is used to calculate the LC tank Rp value using

    the datasheet formula

     

    RP = (RPMAX


  11. Got my EVM and spent yesterday winding a coil and playing around with it.

     

    On the whole this is a great little peripheral and very suitable for close proximity detection. 

    but as a metal detector it suffers too much from pickup and interference 

     

    First I split the EVM into controller, LDC1000 and coil adding 0.1" header connectors.

    The controller to LDC1000 needed a 5x2 header which made it unfriendly for

    direct plugging into a breadboard. 

     

     

    I then wound a 15cm coil suitable for a metal detector, 50 turns of 26awg magnet wire

    wound on the bottom of a plastic bottle. I measured L = 930uH and resonated at 28kHz

    with a 3.7nF cap. The unloaded Q was 43. (wire from a degaussing circuit from

    an old style CRT tv/monitor could be used instead)

     

     

    Unfortunately the coil picks up a lot of interference which you can see as ripple when looking at the

    envelope of the voltage across the coil. This results in considerable variation in

    the frequency count  data and in the Rp proximity data. I adjusted the Fmin, Rpmin, Rpmax

    register settings and the filter cap value so I was sure that the circuit was operating

    correctly as per the datasheet.

     

    Even ignoring the interference I suspect the resonating frequency is too low compared with

    the LDC1000 oscillator gain control loop timing which is reducing the effective resolution of

    the proximity data. 

     

    In a regular metal detector interference is filtered out by various means, unfortunately the

    LDC1000 is a complete control system with limited ablity to modify things. 


  12. To elaborate on MPY a little if I may  :rolleyes:  

    MPY is an ultra easy to use language for microcontrollers based on a subset of Python.

    It is aimed at simple projects using the MSP430 Launchpads.

     

    The syntax is very clean and simple. I claim that programs written in MPY are more

    compact and easier to write than the Arduino style C programs written using sketch/wiring. 

     

    Its currently limited to integer variables but there is a full range of hardware functions

    to control the main peripherals: IOs, ADC, Interrupts, Timers, PWM, Print.  Plus there

    is full access to the MSP430 named Registers for any lowlevel stuff.  

     

    Under the hood MPY is converted to regular C before being compiled using the regular

    mspgcc/mspdebug toolchain, and yes the MPY language is still alive and kicking.

×
×
  • Create New...