<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://w220.wiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Joshuarjs</id>
	<title>W220 S-Class Encyclopedia - User contributions [en]</title>
	<link rel="self" type="application/atom+xml" href="https://w220.wiki/api.php?action=feedcontributions&amp;feedformat=atom&amp;user=Joshuarjs"/>
	<link rel="alternate" type="text/html" href="https://w220.wiki/Special:Contributions/Joshuarjs"/>
	<updated>2026-04-06T11:25:50Z</updated>
	<subtitle>User contributions</subtitle>
	<generator>MediaWiki 1.41.0</generator>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8015</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8015"/>
		<updated>2020-08-17T19:44:56Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learned from experimenting with the PSE, and is not meant to be a guide. This is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Pump Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino RF remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from a smart phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8014</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8014"/>
		<updated>2020-08-17T19:39:05Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learned from experimenting with the PSE, and is not meant to be a guide. This is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Pump Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8013</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8013"/>
		<updated>2020-08-17T19:38:29Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. This is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Pump Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=8011</id>
		<title>File:PSEArdCircuit.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=8011"/>
		<updated>2020-08-17T03:52:12Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs uploaded a new version of File:PSEArdCircuit.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=8010</id>
		<title>File:PSEArdCircuit.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=8010"/>
		<updated>2020-08-17T03:51:02Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs uploaded a new version of File:PSEArdCircuit.png&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8009</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8009"/>
		<updated>2020-08-17T03:49:07Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. This is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Pump Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Pneumatic_System_Equipment_(PSE)_Pump&amp;diff=8008</id>
		<title>Pneumatic System Equipment (PSE) Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Pneumatic_System_Equipment_(PSE)_Pump&amp;diff=8008"/>
		<updated>2020-08-17T03:48:21Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: /* Lessons Learned */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;Back to: [[WIS 80.20 Central Locking System, Interior Central Locking]]&lt;br /&gt;
&lt;br /&gt;
==Description==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE)]] Pump does the closing of the doors and trunk with pressure. It either increases or decreases the pressure in the lines causing the movement of pistons in actuators, which in turn move levers in the various latches, which pull the doors or trunk closed.&lt;br /&gt;
&lt;br /&gt;
Notice that the PSE Pump is very clever, and can both blow (create +ve pressure) and suck (create -ve pressure or vacuum).&lt;br /&gt;
&lt;br /&gt;
The negative pressure (vacuum) pulled by the PSE Pump may ensure retraction of various actuators but it also performs function in it’s own right, such as retracting the Boot/Trunk Handle.&lt;br /&gt;
&lt;br /&gt;
'''Pneumatic System Equipment or PSE Pump in Boot or Trunk'''&lt;br /&gt;
&lt;br /&gt;
[[File:Pneumatic System Equipment or PSE Pump in Boot or Trunk.JPG|600px|center]]&lt;br /&gt;
&lt;br /&gt;
==Functions==&lt;br /&gt;
On a M-B W220 2003 Update S500 LWB:&lt;br /&gt;
* Locking/Unlocking of Doors,&lt;br /&gt;
* Soft/Self Close Function for Trunk,&lt;br /&gt;
* Inflation of Lumbar Support Bladders,&lt;br /&gt;
* Operation of Fuel Filler Flap Lock, (For manual release see [[WIS 47.00 Fuel Filler Cover]]&lt;br /&gt;
* [[WIS 88.52 Retractable Trunk Lid Grip (RTG)|Extension and retraction of the Boot/Trunk Handle]],&lt;br /&gt;
* Releases the Child Safety Lock on Rear Doors in an emergency, and&lt;br /&gt;
* [[WIS 88.50 Trunk/Boot Lid|Operation of the Boot/Trunk Catch for auto opening]].&lt;br /&gt;
&lt;br /&gt;
==Summary of Designations and Functions==&lt;br /&gt;
The W220 S-Class Pneumatic System Equipment (PSE) Pump has each Port designated with Capital Letters:&lt;br /&gt;
&lt;br /&gt;
SK, KAF, HECK, TD, Blank&lt;br /&gt;
&lt;br /&gt;
......FoR, FoL, BFT, FT and MKL.&lt;br /&gt;
&lt;br /&gt;
See next Figure for PSE Pump Air Line Port Designations.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Air Line Port Designations.JPG|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; style=&amp;quot;margin: auto;&amp;quot;&lt;br /&gt;
|+Summary of Designations and Functions- Pneumatic System Equipment (PSE) Pump&lt;br /&gt;
|-&lt;br /&gt;
!style=&amp;quot;text-align:center;&amp;quot;|Pneumatic System Equipment (PSE) Pump Port Connector and Air Line Colour&lt;br /&gt;
!Designation&lt;br /&gt;
!Function in W220 2003 Update S500L&lt;br /&gt;
|-&lt;br /&gt;
|Black connector/large yellow air line&lt;br /&gt;
|SK&lt;br /&gt;
|Main Inlet Line with Air Filter behind the Rear Left Seat Back&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /white air line&lt;br /&gt;
|KAF&lt;br /&gt;
|Rear Seat Head Restraints&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|HECK&lt;br /&gt;
|Retractable Trunk Grip (RTG), Boot/Trunk Catch Actuator and Trunk Soft Close Mechanism&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|TD&lt;br /&gt;
|Fuel Filler Flap Lock&lt;br /&gt;
|-&lt;br /&gt;
|Not Used&lt;br /&gt;
| &lt;br /&gt;
| &lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|FoR&lt;br /&gt;
|Rear Right Door Lock, Child Safety Door Lock Release and Soft/Self Close&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|FoL&lt;br /&gt;
|Rear Left Door Lock , Child Safety Door Lock Release and Soft/Self Close&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|BFT&lt;br /&gt;
|Front Passenger's (left or right depends on LHD or RHD) Door Lock and Soft/Self Close&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /yellow air line&lt;br /&gt;
|FT&lt;br /&gt;
|Front Driver's (left or right depends on LHD or RHD) Door Lock and Soft/Self Close&lt;br /&gt;
|-&lt;br /&gt;
|Grey connector /grey air line&lt;br /&gt;
|MKL&lt;br /&gt;
|Multi Contour Backrest (Lumbar Support Bladder all four seats)&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==Location==&lt;br /&gt;
===PSE Pump===&lt;br /&gt;
The Pneumatic System Equipment (PSE) Pump is located in the Boot/Trunk in a foam lined compartment in the left rear fender well, above the GPS Navigation Unit and is hidden from view by the Boot/Trunk Liner.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Location.jpg|300px|center]]&lt;br /&gt;
&amp;lt;!--[[File:W220 PSE Pump Location_facelift.jpg|300px|center]] --&amp;gt;&lt;br /&gt;
&lt;br /&gt;
===Inlet Air Filter===&lt;br /&gt;
The PSE Pump SK port is attached via a large diameter yellow pneumatic line to the Inlet Air Filter which is located behind the rear left seat back.&lt;br /&gt;
[[File:W220 Filter on End of Pneumatic Line Attached to PSE Port SK.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
==Part Numbers==&lt;br /&gt;
2003 Update W220 S500 OEM PSE Part Number: &lt;br /&gt;
: &amp;gt;PP-TS20&amp;lt;&lt;br /&gt;
: MB 220 800 10 48 [08]&lt;br /&gt;
: BOSCH 0 132 006 381&lt;br /&gt;
: (944)&lt;br /&gt;
: 0022 03190 10 0315 1	001 Made in France&lt;br /&gt;
&lt;br /&gt;
As usual confusion reigns regarding part numbers.&lt;br /&gt;
&lt;br /&gt;
* One BenzWorld Member called his dealer to verify the part number and apparently all the PSE vacuum pumps are the exact same pump, M-B just kept changing the part number every year, &lt;br /&gt;
: 220 800 02 48 is the oldest part number, then keeps going up to &lt;br /&gt;
: 220 800 03 48, &lt;br /&gt;
: 220 800 05 48,&lt;br /&gt;
: 220 800 10 48 etc.&lt;br /&gt;
But it’s all the same pump so they will all work.&lt;br /&gt;
&lt;br /&gt;
* Another BenzWorld member says only the newest pump will work for sure.  The difference is in the electronics basically. Older pumps for example do not support the remote trunk closure option.&lt;br /&gt;
&lt;br /&gt;
* Another post says, I checked the part numbers on the compatibility, and although 220 800 05 48 is an older version than 220 800 11 48, they are interchangeable.&lt;br /&gt;
&lt;br /&gt;
==Specification Values (Obtained by Measurement)==&lt;br /&gt;
===Pressure Regulated Switch===&lt;br /&gt;
The PSE Pump has a Pressure Regulated Switch which is adjustable. It can be accessed once the pump is removed and dismantled.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Pressure Switch.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
The Pressure Regulated Switch changes from a closed position to an open position at 27.6KPa (4psi).&lt;br /&gt;
&lt;br /&gt;
===Pressure at MKL Port===&lt;br /&gt;
Contrary to the result obtained at the Pressure Switch the pressure measured at the MKL (Multicontour backrest) port was 82.7KPa (12psi). The WIS specification states &amp;quot;A pressure of approx. (700...950) mbar is produced at the pump outlet 'MKL'.&amp;quot; and &amp;quot;If the pressure has dropped to (500...650) mbar, the control module operates and produces pressure&amp;quot;.&lt;br /&gt;
&lt;br /&gt;
Thus the PSE Pump (A37) should;&lt;br /&gt;
* switch '''off''' at 700 to 950 mbar or 70 to 95 KPa or 10.1 to 13.8 psi.&lt;br /&gt;
* switch '''on''' at 500 to 650 mbar or 50 to 65 KPa or 7.3 to 9.4 psi.&lt;br /&gt;
&lt;br /&gt;
===Solenoid Coil Resistance===&lt;br /&gt;
The PSE Pump has ten solenoid valves. The coils have a resistance of 34.0 Ohms +/-0.1.&lt;br /&gt;
&lt;br /&gt;
Note the resistance may be measured in situ, ie without unsoldering and removing the printed circuit board.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Coil Resistances.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
==Baseline Pressure Tests==&lt;br /&gt;
In order to establish a base line performance the following pressure tests were conducted and the results recorded as each feature was run through it’s full range of operation.&lt;br /&gt;
&lt;br /&gt;
The pressure readings were obtained with a home made dual gauge set, comprising a Vacuum Gauge and a Pressure Gauge teed together, and then this dual gauge teed into each air line in turn.&lt;br /&gt;
&lt;br /&gt;
The appropriate function was then operated as per normal whilst observing the dual gauges.  By necessity each air line had to be disconnected and then reconnected with the tee piece in line for each test.  This may have some impact on the results as the Pump is very aware that the line has been disconnected.  According to Brett Allison in the reference, the W140 Close Assist Pump will cease to control a particular air line if it detects a fault several times in a row.  This condition is corrected by unplugging the large connector on the PSE Pump, waiting a minute or so and reconnecting, which apparently resets the electronics.&lt;br /&gt;
&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; style=&amp;quot;margin: auto;&amp;quot;&lt;br /&gt;
|+Baseline Pressure Tests&lt;br /&gt;
|-&lt;br /&gt;
!style=&amp;quot;text-align:center;&amp;quot;|PSE Pump Port Designation&lt;br /&gt;
!Function in W220 2003 Update S500 LWB&lt;br /&gt;
!Pressure Tests (Note Non-Existent Soft Close Function on All Doors)&lt;br /&gt;
|-&lt;br /&gt;
|SK&lt;br /&gt;
|Main Inlet Line with Filter&lt;br /&gt;
|Main Inlet Line with Filter behind the Rear Left Seat Back &lt;br /&gt;
|-&lt;br /&gt;
|KAF&lt;br /&gt;
|Rear Seat Head Restraints&lt;br /&gt;
|Switch Head Restraints up, get +ve pressure (27KPa, 4psi), the head restraints go up, then returns to atmospheric pressure.&lt;br /&gt;
Switch Head Restraints down, no change in pressure (atmospheric), Head Restraints go down. &lt;br /&gt;
|-&lt;br /&gt;
|HECK&lt;br /&gt;
|Retractable Trunk Grip (RTG) Boot/Trunk Catch Actuator and Trunk Soft Close Mechanism&lt;br /&gt;
|Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click, get +ve pressure (27KPa, 4psi), Boot/Trunk Catch Actuator pulls boot closed, then –ve pressure (19”Hg vacuum), which retracts RTG Handle, then returns to atmospheric pressure.&lt;br /&gt;
Open Boot/Trunk with either remote control on key fob, driver’s door trunk release switch or switch on trunk lid, get +ve pressure (27KPa, 4psi), which extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
|-&lt;br /&gt;
|TD&lt;br /&gt;
|Fuel Filler Flap Lock&lt;br /&gt;
|Lock car using Remote Key, get +ve pressure (28Kpa or 4psi), which moves pin out to lock Fuel Filler Flap, then returns to atmospheric pressure.&lt;br /&gt;
Unlock car using Remote Key, get -ve pressure (8”Hg vacuum), which retracts pin to unlock Fuel Filler Flap, then returns to atmospheric pressure.&lt;br /&gt;
|-&lt;br /&gt;
|Not Used&lt;br /&gt;
| &lt;br /&gt;
| &lt;br /&gt;
|-&lt;br /&gt;
|FoR&lt;br /&gt;
|Rear Right Door&lt;br /&gt;
|Lock car using Remote Key, get +ve pressure (14Kpa or 2psi), which pulls Rear Right Door Lock Button down, then returns to atmospheric pressure.&lt;br /&gt;
Unlock car using Remote Key, get -ve pressure (9”Hg vacuum), which moves Rear Right Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
Soft Close Feature (Where Fitted TBD)&lt;br /&gt;
|-&lt;br /&gt;
|FoL&lt;br /&gt;
|Rear Left Door&lt;br /&gt;
|Lock car using Remote Key, get +ve pressure (24Kpa or 3.5psi), which pulls Rear Left Door Lock Button down, then returns to atmospheric pressure.&lt;br /&gt;
Unlock car using Remote Key, get -ve pressure (9”Hg vacuum) which moves Rear Left Door Lock Button up, then returns to atmospheric pressure. &lt;br /&gt;
Soft Close Feature (Where Fitted TBD)&lt;br /&gt;
|-&lt;br /&gt;
|BFT&lt;br /&gt;
|Front Passenger's Door (left or right depends on LHD or RHD)&lt;br /&gt;
|Lock car using Remote Key, get +ve pressure (24Kpa or 3.5psi), which pulls Front Left Door Lock Button down, then returns to atmospheric pressure.&lt;br /&gt;
Unlock car using Remote Key, get -ve pressure (9”Hg vacuum), which moves Front Left Door Lock Button up, then returns to atmospheric pressure. &lt;br /&gt;
Soft Close Feature (Where Fitted TBD)&lt;br /&gt;
|-&lt;br /&gt;
|FT&lt;br /&gt;
|Front Driver's Door ((left or right depends on LHD or RHD))&lt;br /&gt;
|Lock car using Remote Key, get +ve pressure (21Kpa or 3psi), which pulls Front Right Door Lock Button down, then returns to atmospheric pressure.&lt;br /&gt;
Unlock car using Remote Key, get -ve pressure (9”Hg vacuum), which moves Front Right Door Lock Button up, then returns to atmospheric pressure. &lt;br /&gt;
Soft Close Feature (Where Fitted TBD)&lt;br /&gt;
|-&lt;br /&gt;
|MKL&lt;br /&gt;
|Multi Contour Backrest (Lumbar Support Bladder all seats)&lt;br /&gt;
|When the MKL Air Line is connected it always has +ve pressure (55Kpa or 8psi).  If the MKL Air Line is disconnected each Lumbar Support Bladder remains inflated until it’s Adjustment Control on the edge of the seat is returned to ‘0’.  You can hear the air escaping from the Adjustment Control.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==Issues==&lt;br /&gt;
===Pump Fails to Work Due to Pneumatic Leaks===&lt;br /&gt;
* The PSE pump contains electronics which has memory and will disable some functions if they do not work properly for whatever reason. For example a leak in a line or actuator may cause the pump to run for too long. The electronics may disable the pump in this situation.&lt;br /&gt;
* The solution is to reset the pump which should restore functionality, even if temporarily. If the fault persists the pump will most likely be disabled again.&lt;br /&gt;
===Pump Fails to Work Due to Blocked Pump Ports===&lt;br /&gt;
* Some functions may not work due to a build up of a fine black powder inside the PSE pump which blocks the relevant port.&lt;br /&gt;
* The solution is to dismantle the pump and clean any contamination from the pump head or internal lines. The following contaminated area was provided by BenzWorld poster, GotBenz.&lt;br /&gt;
[[File:PSE Pump Contaminated Parts.JPG|500px|center]]&lt;br /&gt;
===Pump Fails to Work Due to Over Heating===&lt;br /&gt;
* The Retractable Trunk Grip (RTG) ie the pneumatically controlled hidden chrome handle failed when the car was locked and left parked. Next morning the car wouldn’t unlock because the battery voltage had drained to 6.4V. The PSE pump had been running all night and melted the discharge plastic port on the pump.&lt;br /&gt;
[[File:W220 PSE Pump Melted Discharge Port.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
* In this example the PSE pump output port is still intact but is leaking through a small hole which was created when the heat from the pump softened the plastic. After doing the Internal Leak Testing described below it the pump was found to have a severe internal leak due to heat damage and was unusable.&lt;br /&gt;
[[File:PSE Closeup of Partially Melted Pump Output Port with Annotation.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
* The next photo shows two W220 PSE Pumps with severe external heat damaged base plates. Both pumps were unusable.&lt;br /&gt;
[[File:W220 PSE Pumps Showing External Heat Damaged Base Plates Bottom View.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
* The next photo shows a heat damaged PSE pump which has been cut open to reveal the internal leak.&lt;br /&gt;
[[File:W220 PSE Pump Heat Damaged Base Plate Internal View.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
And a close-up of the leakage path.&lt;br /&gt;
[[File:W220 PSE Pump Internal View Closeup of Failure Mode.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
* The easy solution is to buy a new or second hand pump and after fitting reprogram the pump to the car using STAR.&lt;br /&gt;
&lt;br /&gt;
* If the PSE Pump Output Port is still intact and the pump doesn't show any of the signs of bubbling due to heat, a pressure tensioner can be added for extra strength. See below for DIY Repair.&lt;br /&gt;
&lt;br /&gt;
* Even if the pump is in good condition and doesn't show any signs of damage due to heat it is a good idea to add a heat radiator to remove some of the Output Port heat generated by the pump. See below for DIY Solution.&lt;br /&gt;
&lt;br /&gt;
{|&lt;br /&gt;
|{{#ev:youtube|https://www.youtube.com/watch?v=9vwtFR343SE|320|left|Pump repair. Part 1.|frame}}&lt;br /&gt;
|{{#ev:youtube|https://www.youtube.com/watch?v=f_1JBVw8jjE|320|left|Pump repair. Part 2.|frame}}&lt;br /&gt;
|{{#ev:youtube|https://www.youtube.com/watch?v=pzb3qOghbpA|320|left|Pump repair. Part 3.|frame}}&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==Resetting==&lt;br /&gt;
Resetting of the PSE pump is accomplished by either pulling the 20 amp [[WIS 54.15 Fuse and Relay Box|fuse]] under the Rear Right Seat or disconnecting the main connector to the PSE pump for thirty seconds.&lt;br /&gt;
&lt;br /&gt;
==Accessing==&lt;br /&gt;
'''Warning: DO NOT remove any of the Air Lines before ANNOTATING them. The PSE Pump Ports are marked but the Air Lines are not.'''&lt;br /&gt;
* Remove battery earth connection.&lt;br /&gt;
* Remove the plastic panel at the rear most edge of the Boot/Trunk opening.&lt;br /&gt;
* Remove Trunk/boot left side lining. See [[WIS 88.50 Trunk/Boot Lid]].&lt;br /&gt;
* It helps to remove the Boot/Trunk Lining under the back window after also removing the Battery Cover and the right Boot/Trunk liner but it is not absolutely necessary.&lt;br /&gt;
* It is not necessary to touch either the GPS Navigation or the CD Player.&lt;br /&gt;
* Remove TV Tuner if fitted.&lt;br /&gt;
* Remove insulating cover from PSE Pump.&lt;br /&gt;
* Withdraw PSE Pump from its insulated box.&lt;br /&gt;
* Annotate each line with the designation matching that found on the PSE Pump.&lt;br /&gt;
* Note the Air Lines are connected to the pump by snap-on connectors.&lt;br /&gt;
&lt;br /&gt;
To inspect the internals see section &amp;quot;Dismantling - PSE Pump&amp;quot; below.&lt;br /&gt;
&lt;br /&gt;
==Fault Codes==&lt;br /&gt;
{| class=&amp;quot;wikitable&amp;quot; style=&amp;quot;margin: auto;&amp;quot;&lt;br /&gt;
|+Fault Codes - Pneumatic System Equipment (PSE) Pump&lt;br /&gt;
|-&lt;br /&gt;
!style=&amp;quot;text-align:center;&amp;quot;|Code&lt;br /&gt;
!Fault&lt;br /&gt;
|-&lt;br /&gt;
|B1436-012&lt;br /&gt;
|The safety time of the central locking has been exceeded for the following pneumatic branch: Driver's door.&lt;br /&gt;
|-&lt;br /&gt;
|B1436-014&lt;br /&gt;
|The safety time of the central locking has been exceeded for the following pneumatic branch: Front passenger door or rear doors&lt;br /&gt;
|-&lt;br /&gt;
|B1436-015&lt;br /&gt;
|The safety time of the central locking has been exceeded for the following pneumatic branch: Passenger door.&lt;br /&gt;
|-&lt;br /&gt;
|B1436-016&lt;br /&gt;
|The safety time of the central locking has been exceeded for the following pneumatic branch: Left rear door.&lt;br /&gt;
|-&lt;br /&gt;
|B1436-017&lt;br /&gt;
|The safety time of the central locking has been exceeded for the following pneumatic branch: Right rear door.&lt;br /&gt;
|-&lt;br /&gt;
|B1437&lt;br /&gt;
|The safety time has been exceeded for the following pneumatic branch: Lower or raise rear head restraints.&lt;br /&gt;
|-&lt;br /&gt;
|B1438-011&lt;br /&gt;
|The air demand of the multicontour backrest is too high.&lt;br /&gt;
|-&lt;br /&gt;
|B1438-012&lt;br /&gt;
|The safety time has been exceeded for the following pneumatic branch: Multicontour backrest.&lt;br /&gt;
|-&lt;br /&gt;
|B1440&lt;br /&gt;
|The safety time has been exceeded for the following pneumatic branch: Trunk lid&lt;br /&gt;
remote release.&lt;br /&gt;
|-&lt;br /&gt;
|B1442-012&lt;br /&gt;
|The safety time of the power closing has been exceeded for the following pneumatic branch: Driver's door.&lt;br /&gt;
|-&lt;br /&gt;
|B1442-015&lt;br /&gt;
|The safety time of the power closing has been exceeded for the following pneumatic branch: Passenger door.&lt;br /&gt;
|-&lt;br /&gt;
|B1442-016&lt;br /&gt;
|The safety time of the power closing has been exceeded for the following pneumatic branch: Left rear door.&lt;br /&gt;
|-&lt;br /&gt;
|B1442-017&lt;br /&gt;
|The safety time of the power closing has been exceeded for the following pneumatic branch: Right rear door.&lt;br /&gt;
|-&lt;br /&gt;
|B1442-018&lt;br /&gt;
|The safety time of the power closing has been exceeded for the following pneumatic branch: Trunk lid.&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
==Testing and DIY Repairs==&lt;br /&gt;
&lt;br /&gt;
===Test Pneumatic System by Observation===&lt;br /&gt;
There is an easy test to see if it's all working properly.&lt;br /&gt;
With the boot open and the pump visible, use a screwdriver to carefully trip the catch in the boot lid,&lt;br /&gt;
basically tricking it into thinking it's time to close.&lt;br /&gt;
The catch shuts and you can clearly hear the how long the pump is on for.&lt;br /&gt;
It should stop after no more than 5 seconds. If it runs on to 12-16 seconds,&lt;br /&gt;
it's logging an error and the close assist system will stop working after five or six operations.&lt;br /&gt;
&lt;br /&gt;
After rebuild it should take only 3 seconds to close, before it was taking 16 seconds.&lt;br /&gt;
{|&lt;br /&gt;
|{{#ev:youtube|https://www.youtube.com/watch?v=UpMtQkakOyI|320|left|Testing PSE pump.|frame}}&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
===Test Pneumatic Lines for Leakage===&lt;br /&gt;
The best method for determining which lines are leaking is to perform leakage tests on each pneumatic line when disconnected from the PSE Pump.  Firstly remove the PSE Pump.&lt;br /&gt;
====Remove PSE Pump====&lt;br /&gt;
To access and remove the PSE Pump refer to section &amp;quot;Accessing - Pneumatic System Equipment (PSE) Pump&amp;quot; above.&lt;br /&gt;
&lt;br /&gt;
====Leakage Testing Pneumatic Lines====&lt;br /&gt;
* Carefully prise one pneumatic line from the PSE port.&lt;br /&gt;
* Connect a MityVac hand operated vacuum pump to the open pneumatic line.&lt;br /&gt;
* Apply negative vacuum. (Note some long lines with large actuators will require considerable pumping.&lt;br /&gt;
* Observe the result on the MityVac gauge. It should hold a steady vacuum if there are no leaks.&lt;br /&gt;
* If leaks are observed you will need to work your way towards the relevant actuator and repeat wherever it is convenient.&lt;br /&gt;
* Replace the pneumatic line.&lt;br /&gt;
* Repeat the vacuum test on the next pneumatic line.&lt;br /&gt;
&lt;br /&gt;
[[File:MityVac Hand Operated Vacuum Pump at the PSE Pump End.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
====Leakage Testing Pneumatic Lines Using Smoke Machine ====&lt;br /&gt;
&lt;br /&gt;
{|&lt;br /&gt;
|{{#ev:youtube|https://www.youtube.com/watch?v=m6RP-4Shyos|320|left|Leakage testing using smoke machine.|frame}}&lt;br /&gt;
|}&lt;br /&gt;
&lt;br /&gt;
===Pressure Test Results===&lt;br /&gt;
A vacuum gauge and a pressure gauge were teed together to make a +ve and -ve pressure tester which was then teed into each PSE Pump output port to measure the resulting operational pressures.&lt;br /&gt;
[[File:Vacuum and Pressure Gauges Teed Together.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
See Section above [https://w220.ee/Pneumatic_System_Equipment_(PSE)_Pump#Specification_Values_.28Obtained_by_Measurement.29_-_Pneumatic_System_Equipment_.28PSE.29_Pump]&lt;br /&gt;
&lt;br /&gt;
A thorough description and results of pressure tests can be found at BenzWorld Post #15:&lt;br /&gt;
&lt;br /&gt;
http://www.benzworld.org/forums/w220-s-class/1631298-does-my-s500-have-soft-self-2.html&lt;br /&gt;
&lt;br /&gt;
and 2002 S430 Pneumatic System Equipment (PSE) Pump at:&lt;br /&gt;
&lt;br /&gt;
http://www.benzworld.org/forums/w220-s-class/1571979-pse-pump-air-lines.html&lt;br /&gt;
&lt;br /&gt;
===Internal Pneumatic Schematic===&lt;br /&gt;
A failed PSE Pump was sectioned through the base plate. This allowed the following:&lt;br /&gt;
* investigation of the internal leakage paths, &lt;br /&gt;
* determination of the pneumatic schematic and&lt;br /&gt;
* development of a leakage test method.&lt;br /&gt;
&lt;br /&gt;
'''Schematic of Internal Pneumatic Pathways and Solenoid Valves in Static (Off) Mode'''&lt;br /&gt;
&lt;br /&gt;
Note orientation of diagrams is as viewed from the bottom or port side of the PSE pump.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Viewed from Bottom or Port Side.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump Internal Pneumatic Schematic in Static Mode.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
'''Schematic of Internal Pneumatic Pathways and Solenoid Valves in +ve Pressure Generating Mode'''&lt;br /&gt;
&lt;br /&gt;
The blue highlight shows the air pathway when the PSE Pump is generating positive pressure. Solenoid valve #11 is energised for positive pressure mode. There may be other valves energised as well depending on the demand.&lt;br /&gt;
[[File:W220 PSE Pump Internal Pneumatic Schematic in Positive Pressure Generating Mode.jpg|500px|center]]&lt;br /&gt;
&lt;br /&gt;
'''Schematic of Internal Pneumatic Pathways and Solenoid Valves in Suction, -ve Pressure or Vacuum Generating Mode'''&lt;br /&gt;
&lt;br /&gt;
The green highlight shows the air pathway when the PSE Pump is generating vacuum. Solenoid valve #1 is energised for vacuum mode. There may be other valves energised as well depending on the demand.&lt;br /&gt;
[[File:W220 PSE Pump Internal Pneumatic Schematic in Vaccum Generating Mode.jpg|500px|center]]&lt;br /&gt;
&lt;br /&gt;
'''Schematic of a Typical Internal Pneumatic Pathway Failure'''&lt;br /&gt;
&lt;br /&gt;
As shown in several examples above, excessive heat generated by prolonged operation of the electrical pump will cause softening and subsequent ballooning of the base plate, external damage and eventually internal failure of the pneumatic pathways leading to severe leakage between the pressure port and the main manifold as shown in red in the next image.&lt;br /&gt;
[[File:W220 PSE Pump Internal Pneumatic Schematic Typical Failure Path.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
===Understanding a PSE Pump===&lt;br /&gt;
An excellent article by Brett Allison titled &amp;quot;Getting to know your Closing Assist Pump: Function, Tips, and Fixes&amp;quot; is at:&lt;br /&gt;
&lt;br /&gt;
https://web.archive.org/web/20120418063628/http://v12uberalles.com/Closing_Assist_Pump.htm&lt;br /&gt;
&lt;br /&gt;
===Test Internal Pneumatic Pathways for Leakage===&lt;br /&gt;
A PSE Pump that has overheated may have developed an internal leakage path between the electrical pump pressure port and the main manifold. The usual symptoms are that the pump fails to generate either or both positive pressure and vacuum. A typical failure pathway can be seen in this schematic. &lt;br /&gt;
[[File:W220 PSE Pump Internal Pneumatic Schematic in Internal Leak Testing Mode.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
For this test the SK (Inlet Air Filter) port must be capped or plugged.  An air compressor, which has been set to supply a maximum of 40KPa (6psi), is attached to the base plate pump pressure port.  A pressure gauge is attached to the base plate pump suction port. There should be no pressure showing on the gauge. In this example the faulty PSE base plate has a severe internal leakage and the test gauge is showing a full 6psi reading. This pump is only good for the bin.&lt;br /&gt;
[[File:Internal Leak Testing Heat Damaged PSE Pump.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
===DIY Repair===&lt;br /&gt;
====Dismantling====&lt;br /&gt;
Once the PSE pump is on the bench it can be dismantled:&lt;br /&gt;
* Remove the three Torx screws on the top case.&lt;br /&gt;
[[File:W220 PSE Pump Case Torx Screws.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
* Release the tabs (2 each) on the two grey plastic port surrounds and remove. They are identical. Press the screw driver down in the next photo. &lt;br /&gt;
[[File:W220 PSE Pump Removing Port Covers.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
* Prise open the top and bottom covers using the prise points.&lt;br /&gt;
[[File:W220 PSE Pump Case Prise Open Points.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Remove the white plastic holder at the pump Suction and Discharge Ports. '''Be careful not to lose the port internal fittings.'''&lt;br /&gt;
** The Port closest to the observer in the next photograph is designated 'X' and is the '''discharge''' or +ve pressure port.&lt;br /&gt;
** The Port furthest away from the observer in the next photograph is designated 'Y' and is the '''suction''' or vacuum or -ve pressure port.&lt;br /&gt;
[[File:W220 PSE Pump Discharge and Suction Ports.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Carefully note the location and order of the port internal fittings.&lt;br /&gt;
[[File:W220 PSE Pump Discharge Valve and Suction Filter Location.JPG|400px|center]]&lt;br /&gt;
** The discharge or +ve pressure port designated 'X' has a small diameter rubber '''one way valve''' and holder fitted into it.&lt;br /&gt;
** The suction or vacuum or -ve pressure port designated 'Y' has a small diameter '''gauze filter''' and holder fitted into it.&lt;br /&gt;
[[File:W220 PSE Pump Discharge Valve and Suction Filter Closeup.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
* Unsolder the red and black wires at the pump motor.&lt;br /&gt;
&lt;br /&gt;
* Withdraw the whole internal assembly.&lt;br /&gt;
[[File:W220 PSE Pump Internal Assembly.JPG|500px|center]]&lt;br /&gt;
&lt;br /&gt;
====DIY Output Port Leak Repair====&lt;br /&gt;
If the PSE Pump Output Port has not melted completely and you see small bubbles appearing in the base plate, then it may be possible to prevent it getting any worse. The small pinhole leak shown in the next photo was caused by a burst bubble in the softened plastic base.  The position of the leak can be identified by the triangular pattern of dust. This pump was beyond repair as it also had severe internal leakage.&lt;br /&gt;
[[File:PSE Closeup of Partially Melted Pump Output Port with Annotation.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
If the leak is not attended to soon it will cause the pump to burn out or be damaged beyond repair.&lt;br /&gt;
&lt;br /&gt;
The real problem in attempting a repair is that it is the pressure port that always fails and it can have up to 110 KPa (16psi) internal pressure which can easily blow off any externally applied glue. The solution is, once the applied glue has set, add a metal tensioner plate with a layer of plasti-bond filler underneath it to take the pressure. One of the cover screws holes can be sacrificed to allow a bolt and nut to hold the metal tensioner plate in place.&lt;br /&gt;
&lt;br /&gt;
Here is the method in detail.&lt;br /&gt;
* Apply a dob of super strength super glue (preferably one designed for plastic or difficult to bond materials such as Loctite 406) and allow it to set undisturbed for at least 24 hours.&lt;br /&gt;
&lt;br /&gt;
* Manufacture a metal (aluminium is easier to work than steel but both are suitable) tensioner plate to fit under the adjacent solenoids and around the output port spigot. Make sure it fits well before proceeding. The solenoid valves and the bolt plus the adhesion of the filler prevent the tensioner plate from being blown off.&lt;br /&gt;
[[File:PSE Pump Output Port Tensioner Bracket 01.JPG|300px|center]]&lt;br /&gt;
&lt;br /&gt;
* Drill a 3.5mm hole through the existing cover mounting screw hole and also through the new bracket.&lt;br /&gt;
&lt;br /&gt;
* Clean the area around the output port spigot with suitable degreaser and allow to thoroughly dry.&lt;br /&gt;
&lt;br /&gt;
* Apply a thick layer of Plasti-Bond filler to the area around the output port.&lt;br /&gt;
[[File:PSE Pump Output Port with Plasti Bond Filler.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Immediately place the tensioner plate in place and screw down tightly.&lt;br /&gt;
[[File:PSE Pump Output Port with Tensioner Bracket in Place 01.JPG|400px|center]]&lt;br /&gt;
[[File:PSE Pump Output Port with Tensioner Bracket in Place 02.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Place the 10mm diameter output port pipe over the spigot and press down as far as possible.&lt;br /&gt;
&lt;br /&gt;
* Wipe off any excess filler and allow to set.&lt;br /&gt;
&lt;br /&gt;
If you are lucky this should prevent any further blowouts in the plastic due to excess pump heat. To really be sure and to make the design better than the OEM design, add a heat radiator in the Output Port Pneumatic Line. (See below.)&lt;br /&gt;
&lt;br /&gt;
====DIY Add a Heat Radiator in Output Port Line====&lt;br /&gt;
If you want to avoid your pump from damaging the area around the output port due to heat (as shown above), then the addition of a heat transfer radiator in the output pressure pneumatic line will remove some of the excess heat and should avoid any resulting softening, bubbling and subsequent damage to the plastic base plate.&lt;br /&gt;
&lt;br /&gt;
* Wind 1m of 6mm O/D copper pipe around a suitable mandrill of about 50mm diameter to make a coil.&lt;br /&gt;
&lt;br /&gt;
* Shape the ends to allow fitting of suitable pipes with clamps.&lt;br /&gt;
&lt;br /&gt;
* Slightly flare the ends to act as barbs to help prevent the pipe from being blown off.&lt;br /&gt;
[[File:PSE Pump Output Port Heat Radiator.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Insert the heat radiator coil in the output port pneumatic line as shown in the photo.&lt;br /&gt;
[[File:PSE Pump with Output Port Heat Radiator In Place 01.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* You must use hose clamps on the output port pneumatic line pressure connections to avoid the internal pressure from blowing the pipes off. (The OEM design obviously relies on the fact that the output port pneumatic pipe is constrained between the electric motor port and the PSE base connection and cannot blow off unless the electric pump is removed.)&lt;br /&gt;
&lt;br /&gt;
* Cut a slot in the PSE Pump Cover to suit the radiator pipes.&lt;br /&gt;
[[File:PSE Pump with Output Port Heat Radiator In Place 02.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
* Also cut a slot in the sound insulating cover to allow the heat radiator to sit outside the PSE Pump. Fortunately there is plenty of space around the PSE Pump in the boot to accommodate the heat radiator. Just make sure it is tied down with plastic ties so that it doesn't create a rattle. Fill any gaps around the pipes in the slot with sound insulating material or silicon. It should be air tight to attenuate as much sound as possible.&lt;br /&gt;
&lt;br /&gt;
Firmly secure the Heat Radiator tubing to the metal panel work using plastic ties to avoid any rattles.&lt;br /&gt;
&lt;br /&gt;
[[File:W220 PSE Pump with Heat Radiator.JPG|400px|center]]&lt;br /&gt;
&lt;br /&gt;
When tested after the pump was made to run by opening and closing the trunk several times, it was found that only one coil of the heat radiator got hot.&lt;br /&gt;
&lt;br /&gt;
====DIY Overhaul====&lt;br /&gt;
A thorough description of a PSE Pump Overhaul by BenzWorld Member evolotion is at;&lt;br /&gt;
&lt;br /&gt;
http://www.benzworld.org/forums/w220-s-class/1563160-pse-central-locking-pump-overhall.html&lt;br /&gt;
&lt;br /&gt;
==Lessons Learned==&lt;br /&gt;
===Need to Annotate the Pneumatic Lines===&lt;br /&gt;
* DO NOT remove any of the Air Lines before ANNOTATING them. The PSE Pump Ports are marked but the Air Lines are not.&lt;br /&gt;
===Need to Reprogram a New PSE Pump===&lt;br /&gt;
* A NEW OR USED REPLACEMENT PSE CONTROL MODULE MUST BE PROGRAMMED TO YOUR CAR. This is very, very, very important. The same PSE pump model is used on multiple Benz body styles, and even on the same body style not every car has all of the same options. If it is not programmed (via STAR) it will cause the pump to run much longer than necessary and will burn out the motor.&lt;br /&gt;
&lt;br /&gt;
http://www.benzworld.org/forums/w220-s-class/1654318-pse-soft-close-assist-lessons-learned.html&lt;br /&gt;
&lt;br /&gt;
====TIP to Avoid Reprogramming Replacement Pump====&lt;br /&gt;
You can avoid reprogramming a replacement pump if you swap over the original printed circuit board to the replacement pump. It does require some basic soldering skill. Be careful that you don't splatter solder all over the place and make sure you touch an earthed point before touching any electronic parts to avoid damage due to electrostatic discharge.&lt;br /&gt;
&lt;br /&gt;
====Arduino Controlled PSE Pump====&lt;br /&gt;
If the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a [[Arduino Controlled PSE Pump|custom electronic controller using an Arduino]].&lt;br /&gt;
&lt;br /&gt;
===Do Not Add Additional Lubrication===&lt;br /&gt;
* Reference BenzWorld Member 'evolotion': The PSE pump is made of a material which is self lubricating. Hence if you were to introduce a liquid lubricant such as WD40 into the motor or pump, any deposits generated during normal operation would stick to the liquid, and before you know it the liquid becomes a paste, to be more precise, a grinding paste.&lt;br /&gt;
&lt;br /&gt;
===Fix a Faulty Pump or Pneumatic Lines Promptly===&lt;br /&gt;
* A PSE pump and associated pneumatic lines with a fault should be repaired promptly. If the pump runs continuously or excessively for too long it will burn out. Note this also applies to a new pump which has not been properly programmed to the car. If it doesn't match the car's equipment it will burn out through excessive operation.&lt;br /&gt;
&lt;br /&gt;
===It Is Unsafe to Drive a Car Without a Working PSE Pump===&lt;br /&gt;
* In the event of an accident the PSE pump unlocks all doors and releases the Child Safety Lock on Rear Doors.&lt;br /&gt;
* A non functioning PSE Pump will possibly prevent or at the worst delay first responders from gaining access to a crashed vehicle in the event of an emergency.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8007</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8007"/>
		<updated>2020-08-17T03:45:15Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: /* Arduino Code */&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Pump Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Code&amp;diff=8006</id>
		<title>Arduino Controlled PSE Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Code&amp;diff=8006"/>
		<updated>2020-08-17T03:45:02Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Controlled PSE Code to Arduino Controlled PSE Pump Code&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;#REDIRECT [[Arduino Controlled PSE Pump Code]]&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8005</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8005"/>
		<updated>2020-08-17T03:45:02Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Controlled PSE Code to Arduino Controlled PSE Pump Code&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for the [[Arduino Controlled PSE Pump]].&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8004</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8004"/>
		<updated>2020-08-17T03:44:52Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for the [[Arduino Controlled PSE Pump]].&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Powered_PSE&amp;diff=8003</id>
		<title>Arduino Powered PSE</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Powered_PSE&amp;diff=8003"/>
		<updated>2020-08-17T03:44:36Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Powered PSE to Arduino Controlled PSE Pump&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;#REDIRECT [[Arduino Controlled PSE Pump]]&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8002</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8002"/>
		<updated>2020-08-17T03:44:36Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Powered PSE to Arduino Controlled PSE Pump&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8001</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=8001"/>
		<updated>2020-08-17T03:44:16Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for the [[Arduino Controlled PSE]] pump.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8000</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=8000"/>
		<updated>2020-08-17T03:43:57Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Controlled PSE Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Powered_PSE_Code&amp;diff=7999</id>
		<title>Arduino Powered PSE Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Powered_PSE_Code&amp;diff=7999"/>
		<updated>2020-08-17T03:43:28Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Powered PSE Code to Arduino Controlled PSE Code&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;#REDIRECT [[Arduino Controlled PSE Code]]&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7998</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7998"/>
		<updated>2020-08-17T03:43:28Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Joshuarjs moved page Arduino Powered PSE Code to Arduino Controlled PSE Code&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for the [[Arduino Powered PSE]] pump.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7997</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7997"/>
		<updated>2020-08-17T03:35:51Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for the [[Arduino Powered PSE]] pump.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7996</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7996"/>
		<updated>2020-08-17T03:34:02Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Powered PSE Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7995</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7995"/>
		<updated>2020-08-17T03:33:05Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] performs several functions including locking/unlocking of doors, extension and retraction of the trunk handle and dropping the rear headrests. It consists of an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Powered PSE Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7994</id>
		<title>Arduino Controlled PSE Pump</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump&amp;diff=7994"/>
		<updated>2020-08-17T03:29:25Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Created page with &amp;quot;== Description == The Pneumatic System Equipment (PSE) Pump unit is essentially an electronic controller, an air pump and some solenoid valves. Since the electronic contro...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;== Description ==&lt;br /&gt;
The [[Pneumatic System Equipment (PSE) Pump]] unit is essentially an electronic controller, an air pump and some solenoid valves. Since the electronic controller (printed circuit board) is programmed for the specific vehicle that it is in, if the PSE fails and is being replaced with a new or used one, it needs to be either reprogrammed or the printed circuit board needs to be swapped with the original one. This should retain all your vehicle’s PSE functionality.&lt;br /&gt;
&lt;br /&gt;
However, if the original printed circuit board is faulty and you have no means to reprogram a replacement, an alternate solution is to create a custom electronic controller using an Arduino.&lt;br /&gt;
&lt;br /&gt;
== Cautionary Note ==&lt;br /&gt;
The intent of this page is to document what was learnt from experimenting with the PSE, and is not meant to be a guide. It is not the recommended method of repairing a PSE pump due to its complexity and lack of safety features. It does not connect to the car’s electronics and therefore will not operate as per the manufacturer's intent. This includes some of the convenience features and more importantly, the safety procedures during emergencies.&lt;br /&gt;
&lt;br /&gt;
== Main Components ==&lt;br /&gt;
The main components are an RF remote module, an Arduino, an 8-channel Relay Module and the Mercedes PSE pump with the PCB (printed circuit board) removed. The Arduino reads when a button on the remote is pressed and then opens/closes PSE valves via the relays to achieve the desired action.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdComponents.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
A generic Arduino Uno and a 5V 8-channel Optocoupler Isolation Relay Control Board can be used. The remote control shown is a 433MHz Wireless RF 12v 4-Channel Wireless Remote Control Relay Module.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires1.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdWires2.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== PSE Solenoids==&lt;br /&gt;
In the W220, the PSE has 10 solenoids. Two of them are for switching between positive and negative pressure. The remaining eight route air to/from specific parts in the vehicle ([[Pneumatic System Equipment (PSE) Pump#Internal_Pneumatic_Schematic|More info]]). Running the motor with the appropriate solenoids energized performs a specific action.For example, to unlock the driver's door, the solenoids for negative pressure and the front driver's door (FT) are energized. The motor is run for about 5 seconds, and then the valves are de-energized.&lt;br /&gt;
&lt;br /&gt;
With the Arduino controlling the motor and all the solenoids, performing these sequences is pretty straight forward.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWires.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The solenoids require flyback diodes to prevent sparking at the relay. &lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEWired.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
The front passenger and both rear doors can be combined to keep it simple. This setup skips the seat bladder solenoid since the car it is going in does not have intact seat bladders. The fuel flap lock solenoid has also been skipped since there’s no secondary means to manually unlock/unlatch it in case of a failure.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdPSEClosed.jpg|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== The Trunk ==&lt;br /&gt;
In a W220 without an auto-closing trunk, the PSE pump has three trunk functions - unlocking, soft closing and extending/retracting the hidden handle. This is well documented [[Trunk#Function|here]].&lt;br /&gt;
&lt;br /&gt;
The latch in the trunk lid has its own solenoid valve similar to the ones in the PSE. This needs to be energized to unlock the trunk. The wire to the solenoid is in the smaller 6pin connector that plugs into the PSE. The solenoid already has a flyback diode, so I did not need to add one here.&lt;br /&gt;
&lt;br /&gt;
The trunk also has a sensor/switch that detects when the trunk lid is closed. Relays can be used to isolate the signal going to the Arduino from the one going to the car. When it detects that the lid has been closed, the Arduino initiates the soft-close sequence and retracts the hidden handle (RTG).&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit2.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Power Source ==&lt;br /&gt;
Power to the whole system is drawn from the 10-pin connector that plugs into the PSE unit (Pins 2 and 6). That way the system is protected by the same 20amp fuse. The male connector from the failed PSE board can be repurposed.&lt;br /&gt;
&lt;br /&gt;
The Arduino is powered by a USB car charger and the 5v 8-channel relay is powered by a Mini360 DC-DC Buck Converter set to 5v.&lt;br /&gt;
&lt;br /&gt;
Keeping the Arduino continuously powered all the time will drain an idle car’s battery in a couple of weeks or so. Since the tail parking lights flash when the alarm is armed or disarmed, it can be used as a trigger to turn on a latching circuit that powers the Arduino. The Arduino breaks the latch automatically after 4 hours of inactivity, thereby turning itself off.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit1.png|800px|center]]&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
== Motor Protection ==&lt;br /&gt;
Here are three safety measures to protect the motor from running for too long. &lt;br /&gt;
&lt;br /&gt;
# The Arduino code will only run the motor for a predetermined number of seconds and then stop. It will not run indefinitely.&lt;br /&gt;
&lt;br /&gt;
# The Arduino reads the air pressure from the pressure sensor in the PSE. The sensor runs on 5v from the Arduino and is hooked up to one of the analogue inputs. If the pressure is above (+ive) or below (-ive)  a certain threshold, the motor will stop.&lt;br /&gt;
&lt;br /&gt;
# Power to the motor is routed through an NE555-based 10 second delay timer. Even if something goes wrong with the Arduino or relays and the motor stays on for too long, this module will cut power to it after 10 seconds of running.&lt;br /&gt;
&lt;br /&gt;
[[File:PSEArdCircuit3.png|600px|center]]&lt;br /&gt;
&lt;br /&gt;
== Arduino Code ==&lt;br /&gt;
Here’s the [[Arduino Powered PSE Code]]. Explanations are in the comments.&lt;br /&gt;
&lt;br /&gt;
Double presses and long presses have been implemented. This allows us to perform more than one operation per button. It also makes the remote function more like a traditional keyfob.&lt;br /&gt;
&lt;br /&gt;
== Limitations ==&lt;br /&gt;
* This system currently does not connect to the car’s electronics in any way. So it does not work with any of the buttons in the car or the SmarKey keyfob. It also cannot arm/disarm the alarm. The Arduino remote is required to perform any action. &lt;br /&gt;
&lt;br /&gt;
* The system is not a closed loop, meaning that it does not know if the requested action was actually completed successfully or not. It will send air to the door lock, but it does not know if the door was actually locked or not.&lt;br /&gt;
&lt;br /&gt;
* The soft-close doors do not work. There are solenoids in each door that need to be energized to route air to the soft-close actuators. This has not yet been attempted.&lt;br /&gt;
&lt;br /&gt;
== Further Improvements ==&lt;br /&gt;
'''Collision detection''' - A 3-Axis Accelerometer and Gyroscope Sensor Module such as the MPU6050 can be used to detect an impact or a rollover. The doors can then be unlocked automatically.&lt;br /&gt;
&lt;br /&gt;
'''Auto locking when the car moves''' - Either a GPS module or a CAN shield can be used to obtain the vehicle’s speed. &lt;br /&gt;
&lt;br /&gt;
'''Bluetooth and Wifi''' - A module such as the ESP32 should allow remote control from my phone and enable Alexa/Google integration.&lt;br /&gt;
&lt;br /&gt;
'''Switching to an Arduino Mini Pro''' - These should consume a lot less power, lowering the chance of draining the battery. An Arduino Mega 2560 PRO MINI could be used if more I/O pins are required.&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7993</id>
		<title>Arduino Controlled PSE Pump Code</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=Arduino_Controlled_PSE_Pump_Code&amp;diff=7993"/>
		<updated>2020-08-17T03:25:03Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: Created page with &amp;quot;This is the code for controlling the Mercedes W220 PSE with an Arduino as described here.  &amp;lt;pre&amp;gt; /*  Code for controlling the Mercedes W220 PSE with an Arduino */    // Assign...&amp;quot;&lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;This is the code for controlling the Mercedes W220 PSE with an Arduino as described here.&lt;br /&gt;
&lt;br /&gt;
&amp;lt;pre&amp;gt;&lt;br /&gt;
/*&lt;br /&gt;
 Code for controlling the Mercedes W220 PSE with an Arduino&lt;br /&gt;
*/&lt;br /&gt;
 &lt;br /&gt;
 // Assign Remote Control Pins&lt;br /&gt;
static const int RemA = 10; //A&lt;br /&gt;
static const int RemB = 11; //B&lt;br /&gt;
static const int RemC = 12; //C&lt;br /&gt;
static const int RemD = 13; //D&lt;br /&gt;
&lt;br /&gt;
// Assign PSE Pressure Sensor Pin&lt;br /&gt;
static const int PPin = A0;&lt;br /&gt;
&lt;br /&gt;
// Assign Trunk Lid Switch Pin&lt;br /&gt;
static const int TPin = A1;&lt;br /&gt;
int TrunkPrevState;&lt;br /&gt;
&lt;br /&gt;
// Assign Relay Pins&lt;br /&gt;
static const int RelMotor =  2;&lt;br /&gt;
static const int RelPos =  3;&lt;br /&gt;
static const int RelNeg =  4;&lt;br /&gt;
static const int RelFLDr =  5;&lt;br /&gt;
static const int RelDrs =  6;&lt;br /&gt;
static const int RelTrunk =  8;&lt;br /&gt;
static const int RelHR =  9;&lt;br /&gt;
static const int RelTrunkSol =  7;&lt;br /&gt;
&lt;br /&gt;
// Double Click Variables&lt;br /&gt;
int ButtonAState;&lt;br /&gt;
unsigned long timePress = 0;&lt;br /&gt;
unsigned long timePressLimit = 0;&lt;br /&gt;
int clicks = 0;&lt;br /&gt;
&lt;br /&gt;
// Long Press Variables&lt;br /&gt;
long buttonTimer = 0;&lt;br /&gt;
long longPressTime = 1000;&lt;br /&gt;
boolean buttonActive = false;&lt;br /&gt;
boolean longPressActive = false;&lt;br /&gt;
&lt;br /&gt;
// Assign Arduino Auto Shutdown Relay Pin&lt;br /&gt;
static const int SPin = A2;&lt;br /&gt;
&lt;br /&gt;
// Timer Variable for Auto Shutdown&lt;br /&gt;
unsigned long time;&lt;br /&gt;
unsigned long timeout = 14400000; //4 hours&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void setup() {&lt;br /&gt;
&lt;br /&gt;
  // Define pin modes&lt;br /&gt;
  pinMode(PPin, INPUT);&lt;br /&gt;
  pinMode(TPin, INPUT_PULLUP);&lt;br /&gt;
  pinMode(SPin, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RelMotor, OUTPUT);&lt;br /&gt;
  pinMode(RelPos, OUTPUT);&lt;br /&gt;
  pinMode(RelNeg, OUTPUT);&lt;br /&gt;
  pinMode(RelFLDr, OUTPUT);&lt;br /&gt;
  pinMode(RelDrs, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunk, OUTPUT);&lt;br /&gt;
  pinMode(RelHR, OUTPUT);&lt;br /&gt;
  pinMode(RelTrunkSol, OUTPUT);&lt;br /&gt;
&lt;br /&gt;
  pinMode(RemA, INPUT);&lt;br /&gt;
  pinMode(RemB, INPUT);&lt;br /&gt;
  pinMode(RemC, INPUT);&lt;br /&gt;
  pinMode(RemD, INPUT);&lt;br /&gt;
&lt;br /&gt;
  // Making sure all relays are OFF&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  digitalWrite(RelPos, HIGH);&lt;br /&gt;
  digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  digitalWrite(RelHR, HIGH);&lt;br /&gt;
  digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  digitalWrite(SPin, HIGH);&lt;br /&gt;
&lt;br /&gt;
  // Read trunk's current state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void loop() {&lt;br /&gt;
&lt;br /&gt;
// Auto Shutdown Timer--------------------------------------------------------------&lt;br /&gt;
  time = millis(); // Time elapsed since Arduino started&lt;br /&gt;
  if (time &amp;gt; timeout &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    //Turn off Arduino if trunk is and was closed. Else add 30 seconds to the timer.&lt;br /&gt;
    if (TrunkPrevState == HIGH &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
    {&lt;br /&gt;
      digitalWrite(SPin, LOW);&lt;br /&gt;
    }&lt;br /&gt;
    else&lt;br /&gt;
    {&lt;br /&gt;
      timeout = timeout + 30000;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button A pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemA) == HIGH) &lt;br /&gt;
  {&lt;br /&gt;
    LockAll();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
// Button B pressed once or twice-------------------------------------------------&lt;br /&gt;
// Credit - The_Little_Cousin : https://forum.arduino.cc/index.php?topic=425587.msg2932300#msg2932300&lt;br /&gt;
  if (digitalRead(RemB) == HIGH) {&lt;br /&gt;
    delay(100);&lt;br /&gt;
    if (digitalRead(RemB) == LOW) {&lt;br /&gt;
      if (clicks == 0) {&lt;br /&gt;
        timePress = millis();&lt;br /&gt;
        timePressLimit = timePress + 1000;&lt;br /&gt;
        clicks = 1;&lt;br /&gt;
      }&lt;br /&gt;
      else if (clicks == 1 &amp;amp;&amp;amp; millis() &amp;lt; timePressLimit) {&lt;br /&gt;
        //Double press action&lt;br /&gt;
        UnlockAll();&lt;br /&gt;
&lt;br /&gt;
        //Set variables back to 0&lt;br /&gt;
        timePress = 0;&lt;br /&gt;
        timePressLimit = 0;&lt;br /&gt;
        clicks = 0;&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  //Single press&lt;br /&gt;
  if (clicks == 1 &amp;amp;&amp;amp; timePressLimit != 0 &amp;amp;&amp;amp; millis() &amp;gt; timePressLimit)&lt;br /&gt;
  {&lt;br /&gt;
    timePress = 0;&lt;br /&gt;
    timePressLimit = 0;&lt;br /&gt;
    clicks = 0;&lt;br /&gt;
&lt;br /&gt;
    //Single press action&lt;br /&gt;
    UnlockDriver();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button C long-pressed --------------------------------------------------------------&lt;br /&gt;
// Credit xn1ch1 : https://www.instructables.com/id/Arduino-Dual-Function-Button-Long-PressShort-Press/&lt;br /&gt;
  if (digitalRead(RemC) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    if (buttonActive == false) {&lt;br /&gt;
      buttonActive = true;&lt;br /&gt;
      buttonTimer = millis();&lt;br /&gt;
    }&lt;br /&gt;
    if ((millis() - buttonTimer &amp;gt; longPressTime) &amp;amp;&amp;amp; (longPressActive == false)) {&lt;br /&gt;
      longPressActive = true;&lt;br /&gt;
      //Long-press action - Unlock the trunk&lt;br /&gt;
      UnlockTrunk();&lt;br /&gt;
    }&lt;br /&gt;
  } &lt;br /&gt;
  else {&lt;br /&gt;
    if (buttonActive == true) {&lt;br /&gt;
      if (longPressActive == true) {&lt;br /&gt;
        longPressActive = false;&lt;br /&gt;
      } else {&lt;br /&gt;
        //Short-press action - Nothing&lt;br /&gt;
      }&lt;br /&gt;
      buttonActive = false;&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Button D pressed --------------------------------------------------------------&lt;br /&gt;
  if (digitalRead(RemD) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    DropHeadRest();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
// Trunk lid closed -----------------------------------------------------------------&lt;br /&gt;
// When the trunk state changes from open(LOW) to closed (HIGH)&lt;br /&gt;
  if (TrunkPrevState == LOW &amp;amp;&amp;amp; digitalRead(TPin) == HIGH)&lt;br /&gt;
  {&lt;br /&gt;
    LockTrunk();&lt;br /&gt;
  }&lt;br /&gt;
&lt;br /&gt;
  // Store current trunk state&lt;br /&gt;
  TrunkPrevState = digitalRead(TPin);&lt;br /&gt;
&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockAll()&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
  Lock car with +ve pressure, which pulls the Door Lock Button down, then returns to atmospheric press&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
    digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Remaining Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(5);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockAll()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Doors are locked in 2 steps since there's not enough pressure. Possibly due to a small leak.&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Passenger Doors&lt;br /&gt;
    digitalWrite(RelDrs, LOW);&lt;br /&gt;
      MotorRun(6);&lt;br /&gt;
    digitalWrite(RelDrs, HIGH);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockDriver()&lt;br /&gt;
/*&lt;br /&gt;
  Unlock car with -ve pressure , which moves Driver Door Lock Button up, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Driver Door&lt;br /&gt;
   digitalWrite(RelFLDr, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelFLDr, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void DropHeadRest()&lt;br /&gt;
/*&lt;br /&gt;
  Drop rear headrests with -ve pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  //Rear Seat Head Restraints&lt;br /&gt;
    digitalWrite(RelHR, LOW);&lt;br /&gt;
      MotorRun(3);&lt;br /&gt;
    digitalWrite(RelHR, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void LockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Manually close Boot/Trunk by pulling down on RTG Handle until latch goes click,&lt;br /&gt;
   1) +ve pressure, Boot/Trunk Catch Actuator pulls boot closed,&lt;br /&gt;
   2) –ve pressure, retracts the Retractable Trunklid Grip (RTG) Handle,&lt;br /&gt;
   3) Returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  //Trunk Catch Actuator pulls boot closed&lt;br /&gt;
    MotorRun(7);&lt;br /&gt;
  //-ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, LOW);&lt;br /&gt;
  // Retract RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void UnlockTrunk()&lt;br /&gt;
/*&lt;br /&gt;
   Open Boot/Trunk with trunk latch solenoid and +ve pressure, which&lt;br /&gt;
   extends RTG Handle, and unlocks Boot/Trunk latch, releasing lid &lt;br /&gt;
   which fully opens, then returns to atmospheric pressure.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  //+ve Pressure&lt;br /&gt;
    digitalWrite(RelPos, LOW);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  // Open PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, LOW);&lt;br /&gt;
  // Open Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, LOW);&lt;br /&gt;
  // Open Boot/Trunk latch&lt;br /&gt;
    MotorRun(1.5);&lt;br /&gt;
  // Close Solenoid Valve in trunk lock&lt;br /&gt;
    digitalWrite(RelTrunkSol, HIGH);&lt;br /&gt;
  // Extend RTG Handle&lt;br /&gt;
    MotorRun(4);&lt;br /&gt;
  // Close PSE Trunk HECK valve&lt;br /&gt;
    digitalWrite(RelTrunk, HIGH);&lt;br /&gt;
  //Release Pressure&lt;br /&gt;
    digitalWrite(RelPos, HIGH);&lt;br /&gt;
    digitalWrite(RelNeg, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
void MotorRun(float t)&lt;br /&gt;
/* Turns on motor relay for t seconds&lt;br /&gt;
   Checks PPin for pressure extremes every 100ms and turns off motor if out of bounds.&lt;br /&gt;
*/&lt;br /&gt;
{&lt;br /&gt;
  int pressure;&lt;br /&gt;
  delay (100);&lt;br /&gt;
  &lt;br /&gt;
  //Start the motor&lt;br /&gt;
  digitalWrite(RelMotor, LOW);&lt;br /&gt;
&lt;br /&gt;
  for (int i = 0; i &amp;lt;= (t * 10); i++) // t is converted from sec to multiples of 100ms (delay below)&lt;br /&gt;
  {&lt;br /&gt;
    pressure = analogRead(PPin);&lt;br /&gt;
    if (i &amp;gt; 10)  // Only check after 1 sec has passed to ignore spikes at startup&lt;br /&gt;
    {&lt;br /&gt;
      if (pressure &amp;lt; 80 || pressure &amp;gt; 640)&lt;br /&gt;
      {&lt;br /&gt;
        // Immediately stop motor and exit function&lt;br /&gt;
        digitalWrite(RelMotor, HIGH);&lt;br /&gt;
        delay (100);&lt;br /&gt;
        return;&lt;br /&gt;
      }&lt;br /&gt;
      else&lt;br /&gt;
      {&lt;br /&gt;
        delay (100); //Wait and recheck&lt;br /&gt;
      }&lt;br /&gt;
    }&lt;br /&gt;
  }&lt;br /&gt;
  // Stop the motor after t secs have passed&lt;br /&gt;
  digitalWrite(RelMotor, HIGH);&lt;br /&gt;
  delay (100);&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
//--------------------------------------------------------------------------------------------------------&lt;br /&gt;
&lt;br /&gt;
&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit3.png&amp;diff=7992</id>
		<title>File:PSEArdCircuit3.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit3.png&amp;diff=7992"/>
		<updated>2020-08-17T01:33:39Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit1.png&amp;diff=7991</id>
		<title>File:PSEArdCircuit1.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit1.png&amp;diff=7991"/>
		<updated>2020-08-17T01:32:46Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit2.png&amp;diff=7990</id>
		<title>File:PSEArdCircuit2.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit2.png&amp;diff=7990"/>
		<updated>2020-08-17T01:32:16Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdPSEClosed.jpg&amp;diff=7989</id>
		<title>File:PSEArdPSEClosed.jpg</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdPSEClosed.jpg&amp;diff=7989"/>
		<updated>2020-08-17T01:31:18Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdPSEWired.png&amp;diff=7988</id>
		<title>File:PSEArdPSEWired.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdPSEWired.png&amp;diff=7988"/>
		<updated>2020-08-17T01:30:49Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdPSEWires.jpg&amp;diff=7987</id>
		<title>File:PSEArdPSEWires.jpg</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdPSEWires.jpg&amp;diff=7987"/>
		<updated>2020-08-17T01:29:50Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdWires2.jpg&amp;diff=7986</id>
		<title>File:PSEArdWires2.jpg</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdWires2.jpg&amp;diff=7986"/>
		<updated>2020-08-17T01:26:34Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdWires1.jpg&amp;diff=7985</id>
		<title>File:PSEArdWires1.jpg</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdWires1.jpg&amp;diff=7985"/>
		<updated>2020-08-17T01:25:53Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdComponents.png&amp;diff=7984</id>
		<title>File:PSEArdComponents.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdComponents.png&amp;diff=7984"/>
		<updated>2020-08-17T00:56:01Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
	<entry>
		<id>https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=7983</id>
		<title>File:PSEArdCircuit.png</title>
		<link rel="alternate" type="text/html" href="https://w220.wiki/index.php?title=File:PSEArdCircuit.png&amp;diff=7983"/>
		<updated>2020-08-17T00:49:36Z</updated>

		<summary type="html">&lt;p&gt;Joshuarjs: &lt;/p&gt;
&lt;hr /&gt;
&lt;div&gt;&lt;/div&gt;</summary>
		<author><name>Joshuarjs</name></author>
	</entry>
</feed>