Control PWM fan speed depending on tempature

Have you tried HIGH and LOW? I wouldn't assume whether the fan is enabled by a high or low pwm value, so test it to find out.

Both

analogWrite(pwmPin, HIGH);

and

analogWrite(pwmPin, LOW);

Have the same effect... it causes the fan to go slow (~1,800-2,000 RPMS)

That high of a rate can be achieved with a 16MHz clock. 16,000,000 / 256 = 62,500 max pulse rate. Using one of the up/down phase correct modes would cut that roughly in half. That still leaves it a little high though.

So what do you suggest?

int pwmPin     = 9; // digital PWM pin 9
int pwmVal     = 1; // The PWM Value
unsigned long time;
unsigned int rpm;

void setup()
{
    pinMode(pwmPin, 0);      // Sets the pin as output
    analogWrite(pwmPin, 0);  // Sets the pin as input
    digitalWrite(2, HIGH);   // Starts reading
    Serial.begin(9600);
}

void loop()
{
    if (pwmVal <= 251) {
      analogWrite(pwmPin, pwmVal);
      //pwmVal += 10;
      Serial.print(pwmVal);  // Print red value
      Serial.print("\n");    // Print a tab
    } else {
      Serial.print('at max high');  // Print red value
      Serial.print("\n");    // Print a tab
    }
  
    time=pulseIn(2,HIGH);
    rpm=(1000000*60)/(time*4);
    Serial.println(rpm,DEC);
    
    delay(700);
}

StealthRT:
Both

analogWrite(pwmPin, HIGH);

and

analogWrite(pwmPin, LOW);

Have the same effect... it causes the fan to go slow (~1,800-2,000 RPMS)

You need to pass those values to digitalWrite(), not analogWrite(). Alternatively, call analogWrite() with 0 and 255. Passing HIGH and LOW to analogWrite() does not make sense.

Shouldn't you be applying the PWM signal to the BLUE wire and not the yellow?

Yes i do have it connected to the BLUE wire of the fan.

And digitalWrite can not produce a PWM signal...

Simple Pulse Width Modulation with analogWrite
The Arduino's programming language makes PWM easy to use; simply call analogWrite(pin, dutyCycle), where dutyCycle is a value from 0 to 255, and pin is one of the PWM pins (3, 5, 6, 9, 10, or 11). The analogWrite function provides a simple interface to the hardware PWM, but doesn't provide any control over frequency. (Note that despite the function name, the output is a digital signal, often referred to as a square wave.)
Probably 99% of the readers can stop here, and just use analogWrite, but there are other options that provide more flexibility.
Bit-banging Pulse Width Modulation

You can "manually" implement PWM on any pin by repeatedly turning the pin on and off for the desired times. e.g.
void setup()
{
pinMode(13, OUTPUT);
}

void loop()
{
digitalWrite(13, HIGH);
delayMicroseconds(100); // Approximately 10% duty cycle @ 1KHz
digitalWrite(13, LOW);
delayMicroseconds(1000 - 100);
}
This technique has the advantage that it can use any digital output pin. In addition, you have full control the duty cycle and frequency. One major disadvantage is that any interrupts will affect the timing, which can cause considerable jitter unless you disable interrupts. A second disadvantage is you can't leave the output running while the processor does something else. Finally, it's difficult to determine the appropriate constants for a particular duty cycle and frequency unless you either carefully count cycles, or tweak the values while watching an oscilloscope.

StealthRT:
And digitalWrite can not produce a PWM signal...

Well, in a sense it can: digitalWrite(pin, LOW) produces a 0% duty cycle pwm signal aka permanent low; digitalWrite(pin, HIGH) produces a 100% pwm signal aka permanent high. If you have understood the motor signals correctly, one of these should correspond to 'off' and the other should correspond to 'full power'. But so far we don't know whether that's the case or which is which. I suggest you find out.

PeterH:

StealthRT:
And digitalWrite can not produce a PWM signal...

Well, in a sense it can: digitalWrite(pin, LOW) produces a 0% duty cycle pwm signal aka permanent low; digitalWrite(pin, HIGH) produces a 100% pwm signal aka permanent high. If you have understood the motor signals correctly, one of these should correspond to 'off' and the other should correspond to 'full power'. But so far we don't know whether that's the case or which is which. I suggest you find out.

Neither LOW nor HIGH made any impact on the fan... It was 100%.

StealthRT:
Neither LOW nor HIGH made any impact on the fan... It was 100%.

In that case I suggest that either you're wrong about how the fan is intended to be controlled, or you're driving it with the wrong levels.

If the fan is designed to be PWM modulated at 25kHz, then 500Hz is likely to lead to weird behavior. I suspect that is the whole problem.

afremont:
If the fan is designed to be PWM modulated at 25kHz, then 500Hz is likely to lead to weird behavior. I suspect that is the whole problem.

What would you expect to happen when the 25KHz pwm signal goes to 0% or 100% duty cycle?

PeterH:

afremont:
If the fan is designed to be PWM modulated at 25kHz, then 500Hz is likely to lead to weird behavior. I suspect that is the whole problem.

What would you expect to happen when the 25KHz pwm signal goes to 0% or 100% duty cycle?

I get your point, but we already know what happens at that those limits right? At 0%, the fan runs at approx 1200RPM (which is the slowest it goes according to the datasheet, I wouldn't expect it to stop as I've never seen a motherboard PWM a fan any slower than about 1200RPM), and at 100% it goes max speed. It's doing that already, isn't it? It just ignores everything in between because the pulse rate is way off. Even at a duty cycle of 1 the pulse is incredibly wide compared to what it was expecting.

We can guess all day what might be happening, but as long as the datasheet isn't being respected then nobody has a right to expect anything sensible out of its behavior.

afremont:
we already know what happens at that those limits right? At 0%, the fan runs at approx 1200RPM (which is the slowest it goes according to the datasheet, I wouldn't expect it to stop as I've never seen a motherboard PWM a fan any slower than about 1200RPM), and at 100% it goes max speed. It's doing that already, isn't it?

Is it? I haven't seen any suggestion that anything the OP tried is having any effect on the fan speed. If this is controlled by plain old PWM in the range of 0% - 100% then I would expect constant HIGH and LOW values to represent the extreme limits of the controllable speed regardless of the PWM frequency. Do you agree?

StealthRT:
I hooked the incorrect pin on the fan for the PWM so now it does change speeds but when i put it on "1" its still pretty loud/fast. Its spinning about 2,040 RPMs on "1".

This is reply #18 it appears that it does change speeds as I said, just not like he expects. With an analog write of 1, it still runs at 2040RPM. A duty cycle of 1 at 500Hz is 60 times wider than the pulse would be at 30kHz. That sounds like a reasonable explanation for the 2040RPM instead of 1200RPM to me.

I wish the OP would just take the BLUE wire and connect it to ground and then connect it to Vcc and tell us what happens with each.

afremont:

StealthRT:
I hooked the incorrect pin on the fan for the PWM so now it does change speeds but when i put it on "1" its still pretty loud/fast. Its spinning about 2,040 RPMs on "1".

This is reply #18 it appears that it does change speeds as I said, just not like he expects. With an analog write of 1, it still runs at 2040RPM. A duty cycle of 1 at 500Hz is 60 times wider than the pulse would be at 30kHz. That sounds like a reasonable explanation for the 2040RPM instead of 1200RPM to me.

I wish the OP would just take the BLUE wire and connect it to ground and then connect it to Vcc and tell us what happens with each.

Hooking the blue wire to ground slows it down (seems to be the same RPM as the "1") and giving it 12v does nothing... same speed (100%).

Maybe this could help you! It run on Arduino code, but is small enough for the project at hand.

http://www.kickstarter.com/projects/1608192864/rfduino-iphone-bluetooth-40-arduino-compatible-boa?play=1&ref=search

StealthRT:
Hooking the blue wire to ground slows it down (seems to be the same RPM as the "1") and giving it 12v does nothing... same speed (100%).

So grounding it slows it down and hooking it to 12V makes it go full speed. Now try something like this:

  int x, y;
  for(x = 0; x < 40; x++) {
    for(y = 0; y < 25000; y++) {
      digitalWrite(PWMPin, HIGH);
      delayMicroseconds(x);
      digitalWrite(PWMPin, LOW);
      delayMicroseconds(40-x);
    }
  }

That should approximate a 25Khz PWM signal that varies in duty cycle from 0 to 100% spaced across 40 steps. See if your fan runs at different speeds with this. It should start off at 1200RPM approx and increase to full speed over the course of about 40 seconds or so.

afremont:

StealthRT:
Hooking the blue wire to ground slows it down (seems to be the same RPM as the "1") and giving it 12v does nothing... same speed (100%).

So grounding it slows it down and hooking it to 12V makes it go full speed. Now try something like this:

  int x, y;

for(x = 0; x < 40; x++) {
   for(y = 0; y < 25000; y++) {
     digitalWrite(PWMPin, HIGH);
     delayMicroseconds(x);
     digitalWrite(PWMPin, LOW);
     delayMicroseconds(40-x);
   }
 }




That should approximate a 25Khz PWM signal that varies in duty cycle from 0 to 100% spaced across 40 steps. See if your fan runs at different speeds with this. It should start off at 1200RPM approx and increase to full speed over the course of about 40 seconds or so.

It stays at 100% RPMS. Never a decrees.

That doesn't seem right, because it should start off at 0% duty cycle. You did set the pinMode to OUTPUT, right? I haven't tested the code yet, but I will in the morning. If you let the BLUE wire "float" unconnected, the fan runs at full speed, right? Make sure you set the pinMode to OUTPUT.

OOOOPS Make y and unsigned int or make it a long.