Library for RAM chip

I don't know if this is the right place to post this, but i was wondering if someone could create a library out of this file for me, every time I try it never works. I made a program to read/write to a RAM chip with 8 addresses pins and 4 I/O pins, the one defined in the integers is the AM9111.

You may change anything including the voids and integers if it will make it easier.

Here is the code:

int addr[] = {0,1,2,3,4,5,6,7}; //address pins
int od = 12; //Output Disable pin; to read, must be low
int we = 13; //Write Enable pin(in this case on inverted write enable); to write must be low
int io[] = {8,9,10,11}; // Input/Output pins
//          ^LSB    ^MSB
int ios[] = {0,0,0,0}; //I/O Storage, used to store arduio arduino input bits

void w(int b0, int b1, int b2, int b3) //Write to RAM
{
  pinMode(io[0],OUTPUT);
  pinMode(io[1],OUTPUT);
  pinMode(io[2],OUTPUT);
  pinMode(io[3],OUTPUT);
  digitalWrite(od,1);
  digitalWrite(we,0);
  delay(2); //give the chip time
  digitalWrite(io[0],b0);//<-|
  digitalWrite(io[1],b1);//  | set address values
  digitalWrite(io[2],b2);//  |
  digitalWrite(io[3],b3);//<-|
  delay(2); //give the chip time
  digitalWrite(we,1);
  digitalWrite(od,0);
}

void addrSet(int a0,int a1,int a2,int a3,int a4,int a5,int a6,int a7) //Set address on RAM
{
  
  digitalWrite(addr[0],a0);//<-|
  digitalWrite(addr[1],a1);//  |
  digitalWrite(addr[2],a2);//  |
  digitalWrite(addr[3],a3);//  |set address to write/read to/from
  digitalWrite(addr[4],a4);//  |
  digitalWrite(addr[5],a5);//  |
  digitalWrite(addr[6],a6);//  |
  digitalWrite(addr[7],a7);//<-|
  delay(5); //give chip time
  
}

void r() //read from I/O on RAM
{
  pinMode(io[0],INPUT);
  pinMode(io[1],INPUT);
  pinMode(io[2],INPUT);
  pinMode(io[3],INPUT);
  delay(100);
  ios[0] = digitalRead(io[0]);
  ios[1] = digitalRead(io[1]);
  ios[2] = digitalRead(io[2]);
  ios[3] = digitalRead(io[3]);
}

void serialTrans()
{
  Serial.print("---->\n");
  Serial.print(ios[0]);
  Serial.print(ios[1]);
  Serial.print(ios[2]);
  Serial.print(ios[3]);
  Serial.print("\n---->\n");
}

void setup()
{
  Serial.begin(9600);
  digitalWrite(od,0);
  digitalWrite(we,1);
}

void loop() {}

Thanks in advance. :slight_smile:

RAM.pde (1.73 KB)

Here is the Datasheet if needed: http://pdf1.alldatasheet.com/datasheet-pdf/view/143521/ETC1/AM9111.html

you use pin 0 and 1 these are also the hardware serial pins - Didn't you get problems with that?

I would make the interface of the library a bit more userfriendly, the setting of the addres is horror imho, setting individual pins as param is no good programming practice :wink:

Have you read through this one? - http://www.arduino.cc/en/Hacking/LibraryTutorial ?

This is how I would start (not compiled but it is the framework), you only need to implement the details of the functions: _setAddress(), _read(), _write();

succes,
Rob

.h

#ifndef AM9111_h
#define AM9111_h
// 
//    FILE: AM9111.h
//  AUTHOR: Rob Tillaart
// PURPOSE: AM9111library for Arduino
// VERSION: 0.1.00
// HISTORY: See AM9111.cpp
//
// LICENSE: Released to the public domain
//
class AM9111
{
  public:
    AM9111(uint8_t outputDisablePin, uint8_t writeEnablePin);  // constructor wit two pind
    int read(unsigned int address);
    int write(unsigned int address, uint8_t value);
  private:
    void _setAddress(unsigned int address);
    int _read();
    int write(uint8_t value);
    // internal pin admin
    uint8_t _odp;  
    uint8_t _wep;
};
#endif

.cpp

// 
//    FILE: AM9111.cpp
//  AUTHOR: Rob Tillaart
// VERSION: 0.1.00
// PURPOSE: AM9111library for Arduino
//
// HISTORY: 
// 0.1.00 - 2011-04-12 initial version
// 
// LICENSE: Released to the public domain
//

#include "AM9111.h"

/////////////////////////////////////////
//
// PUBLIC
//
AM9111::AM9111(uint8_t outputDisablePin, uint8_t writeEnablePin)
{
  _odp = outputDisablePin;
  _wep = writeEnablePin;
}

int AM9111::read(unsigned int address)
{
  int rv = 0;
  _setAddress(address);
  rv = _read();
  return rv;
}

int AM9111::write(unsigned int address, uint8_t value)
{
  int rv = 0;
  _setAddress(address);
  rv = _write(value);
  return rv;
}

/////////////////////////////////////////
//
// PRIVATE
//
void AM9111::_setAddress(unsigned int address)
{
  // TODO
}


int AM9111::_read()
{
  int rv = 0;
  // TODO
  return rv;
}


int AM9111::_write(uint8_t value)
{
  int  rv = 0;
  // TODO
  return rv;
}

-- update --

personally I think you should use a shift register like the 74HC595 => far lesser lines to use the RAM module
Overruled by insights of Crossroads below

Thanks, I will try it. :slight_smile: The problem with the shift register is that i don't have one, and I'm 13, so i cant just go out and buy it.

How do i use the address with an unsigned int? because it has to control 8 pins... Sorry if I'm asking too much.

@farlepet,
check out these shift registers
http://www.dipmicro.com/store/74HC595
35 cents, lowest shipping around. Order a couple.

How do i use the address with an unsigned int? because it has to control 8 pins... Sorry if I'm asking too much.

(HW advice removed)

int address;
for(int p=0; p<8; p++)
{
  pinMode(p, OUTPUT);
  digitalWrite(p, bitRead(address, p));  // http://www.arduino.cc/en/Reference/BitRead
}

Sorry if I'm asking too much.

Please take my advice and spend a few days to work through the examples in the tutorials and through the reference pages. You will learn a lot there, really

The external RAM also needs control lines - Chip Select, Write Enable, Read Enable (or can maybe tie it low depending on the part, will change mode when WE becomes active)

HC595 does not do data both directions - if its a parallel RAM, then a part like 74A299PC (56 cents at Newark) will be better, can shift out to load the RAM, and shift in to read it.

Serial RAM has same function internally.

I need sleep ...

@CrossRoads,
You are absolutely right, the RAM need to be read also :blush: so the 595 will only do half the trick
I'll update my prev post

The problem with the shift register is that i don't have one, and I'm 13, so i cant just go out and buy it.

I can understand age restrictions on the purchase of weapons and alcohol, but shift registers?
Crazy.

AWOL:

The problem with the shift register is that i don't have one, and I'm 13, so i cant just go out and buy it.

I can understand age restrictions on the purchase of weapons and alcohol, but shift registers?
Crazy.

Perhaps with a permission note from his parents?

Lefty

OK, i got it now, I didn't know that there was a way to read specific bits from a number, i will start working on it.

And by saying that I'm 13, i meant i cant drive out and get one, i don't have a credit card, and my parents don't know much about electrical things, and they don't like to buy stuff online very much, especially if they don't know what it is. But maybe they will be OK with it with that website with the 35 cent shift register.

dipmicro is very good, I have bought a lot of things from them.

Yeah, I just wish Radio Shack had things like that, and that they were less expensive.

Thanks for the help, I just have one more error:

C:\Program Files (x86)\arduino-0022\libraries\AM9111\AM9111.cpp: In member function 'int AM9111::_read()':
C:\Program Files (x86)\arduino-0022\libraries\AM9111\AM9111.cpp:74: error: lvalue required as left operand of assignment

and here is my code:

header:

#ifndef AM9111_h
#define AM9111_h


#include "WProgram.h"

class AM9111
{
  public:
    AM9111(uint8_t outputDisablePin, uint8_t writeEnablePin);  // constructor wit two pind
    int read(unsigned int address);
    int write(unsigned int address, uint8_t value);
    int setIO(uint8_t IO0, uint8_t IO1, uint8_t IO2, uint8_t IO3);

  private:
    void _setAddress(unsigned int address);
    int _read();
    int _write(uint8_t value);
    // internal pin admin
    uint8_t _odp;  
    uint8_t _wep;
    uint8_t _IO[];
    uint8_t _rbits;
};
#endif

source:

#include "AM9111.h"
#include "WProgram.h"

/////////////////////////////////////////
//
// PUBLIC
//
AM9111::AM9111(uint8_t outputDisablePin, uint8_t writeEnablePin)
{
  _odp = outputDisablePin;
  _wep = writeEnablePin;
}

int AM9111::setIO(uint8_t IO0, uint8_t IO1, uint8_t IO2, uint8_t IO3)
{
  _IO[0] = IO0;
  _IO[1] = IO1;
  _IO[2] = IO2;
  _IO[3] = IO3;
}
  

int AM9111::read(unsigned int address)
{
  int rv = 0;
  _setAddress(address);
  rv = _read();
  return rv;
}

int AM9111::write(unsigned int address, uint8_t value)
{
  int rv = 0;
  _setAddress(address);
  rv = _write(value);
  return rv;
}

/////////////////////////////////////////
//
// PRIVATE
//
void AM9111::_setAddress(unsigned int address)
{
for(int p=0; p<8; p++)
{
  pinMode(p, OUTPUT);
  digitalWrite(p, bitRead(address, p));
}
}


int AM9111::_read()
{
  digitalWrite(_odp,0);
  digitalWrite(_wep,1); 
  int rv = 0;
  bitWrite(_rbits,0,digitalRead(_IO[0]));
  bitWrite(_rbits,1,digitalRead(_IO[1]));
  bitWrite(_rbits,2,digitalRead(_IO[2]));
  bitWrite(_rbits,3,digitalRead(_IO[3]));
  _read() = _rbits;
  return rv;
}


int AM9111::_write(uint8_t value)
{
  digitalWrite(_odp,1);
  digitalWrite(_wep,0);
  int  rv = 0;
  digitalWrite(_IO[0],bitRead(0,value));
  digitalWrite(_IO[1],bitRead(1,value));
  digitalWrite(_IO[2],bitRead(2,value));
  digitalWrite(_IO[3],bitRead(3,value));
  return rv;
}

Program:

#include <AM9111.h>

AM9111 ram(12,13);

void setup()
{
  Serial.begin(9600);
  ram.setIO(8,9,10,11);
  ram.write(0,12);
  Serial.print("Read: ");
  Serial.print(ram.read(0));
};
void loop(){};

_read() = _rbits;

What about it?

_read isn't a function returning a reference, so the assignment isn't possible.

OK, so how would I make it so you could do a statement like: Serial.print(AM9111.read()); ?

int AM9111::_read()
{
  digitalWrite(_odp,0);
  digitalWrite(_wep,1); 
  int rv = 0;
  bitWrite(_rbits,0,digitalRead(_IO[0]));
  bitWrite(_rbits,1,digitalRead(_IO[1]));
  bitWrite(_rbits,2,digitalRead(_IO[2]));
  bitWrite(_rbits,3,digitalRead(_IO[3]));
  _read() = _rbits;
  return rv;
}

Have you ever thought why this routine would always return zero? (if it were to compile)
Is that what you want?