aboutsummaryrefslogblamecommitdiff
path: root/flow-core/src/main/scala/ch/jodersky/flow/Serial.scala
blob: 43b1d19df1da9c8185c935960f54f207637a6857 (plain) (tree)
1
2
3
4
5
6
7
8
9
                        
 
                              
                           
 
                                                       
                                               
 
                                                  
                      
 
                                                                                                                              
                               
 
                                                                                                                      
                             

                              
                                                                             

     


                                                                                                      
                                                                                                                                            




                                                                                                                                             
                                            
                                                    
                                                          
     
                                                                                                 




                                                                                                     
                                                                         
    
                                           
     
                                               

     


                                                                                                

                                          
     
                                                     

     





                                                                                                             
                    
    
                                           

                                                                                                                        
     
                                                                               
 


                                                           


                                                            
 





                                                                                              
                                   

     

                            
                                                                        
     
                                  
 






                                                                                                        
                                                                   

                                            
                                                                    



                   
                                                                                            














                                                                       







                                                                                 
 
package ch.jodersky.flow

import akka.actor.ExtensionKey
import akka.util.ByteString

/** Defines messages used by flow's serial IO layer. */
object Serial extends ExtensionKey[SerialExt] {

  /** Base trait for any flow-related messages. */
  sealed trait Message

  /** A message extending this trait is to be viewed as a command, an out-bound message issued by the client to flow's API. */
  trait Command extends Message

  /** A message extending this trait is to be viewed as an event, an in-bound message issued by flow to the client. */
  trait Event extends Message

  /** A command has failed. */
  case class CommandFailed(command: Command, reason: Throwable) extends Event

  /**
   * Open a new serial port.
   *
   * Send this command to the serial manager to request the opening of a serial port. The manager will
   * attempt to open a serial port with the specified parameters and, if successful, create a `SerialOperator` actor associated to the port.
   * The operator actor acts as an intermediate to the underlying native serial port, dealing with threading issues and dispatching messages.
   *
   * In case the port is successfully opened, the operator will respond with an `Opened` message.
   * In case the port cannot be opened, the manager will respond with a `CommandFailed` message.
   *
   * @param port name of serial port to open
   * @param settings settings of serial port to open
   * @param bufferSize maximum read and write buffer sizes
   */
  case class Open(port: String, settings: SerialSettings, bufferSize: Int = 1024) extends Command

  /**
   * A port has been successfully opened.
   *
   * Event sent by a port operator, indicating that a serial port was successfully opened. The sender
   * of this message is the operator associated to the given serial port.
   *
   * @param port name of opened serial port
   */
  case class Opened(port: String) extends Event

  /**
   * Data has been received.
   *
   * Event sent by an operator, indicating that data was received on the operator's serial port.
   *
   * @param data data received on the port
   */
  case class Received(data: ByteString) extends Event

  /**
   * Write data to a serial port.
   *
   * Send this command to an operator to write the given data to its associated serial port.
   * An acknowledgment may be set, in which case it is sent back to the sender on a successful write.
   * Note that a successful write does not guarantee the actual transmission of data through the serial port,
   * it merely guarantees that the data has been stored in the operating system's kernel buffer, ready to
   * be transmitted.
   *
   * @param data data to be written to port
   * @param ack acknowledgment sent back to sender once data has been enqueued in kernel for sending (the acknowledgment
   * is a function 'number of bytes written => event')
   */
  case class Write(data: ByteString, ack: Int => Event = NoAck) extends Command

  /**
   *  Special type of acknowledgment that is not sent back.
   */
  case object NoAck extends Function1[Int, Event] {
    def apply(length: Int) = sys.error("cannot apply NoAck")
  }

  /**
   *  Request closing of port.
   *
   *  Send this command to an operator to close its associated port. The operator will respond
   *  with a `Closed` message upon closing the serial port.
   */
  case object Close extends Command

  /**
   * A port has been closed.
   *
   * Event sent from operator, indicating that its port has been closed.
   */
  case object Closed extends Event

  /**
   * Watch a directory for new ports.
   *
   * Send this command to the manager to get notifications when a new port (i.e. file) is created in
   * the given directory.
   * In case the given directory cannot be watched, the manager responds with a `CommandFailed` message.
   *
   * Note: the sender is also notified of currently existing ports.
   *
   * @param directory the directory to watch
   * @param skipInitial don't get notified of already existing ports
   *
   * @see Unwatch
   * @see Connected
   */
  case class Watch(directory: String = "/dev", skipInitial: Boolean = false) extends Command

  /**
   * Stop receiving notifications about a previously watched directory.
   *
   * @param directory the directory to unwatch
   */
  case class Unwatch(directory: String = "/dev") extends Command

  /**
   * A new port (i.e. file) has been detected.
   *
   * @param port the absolute file name of the connected port
   */
  case class Connected(port: String) extends Event

  /**
   * Sets native debugging mode. If debugging is enabled, detailed error messages
   * are printed (to stderr) from native method calls.
   *
   * @param value set to enable debugging
   */
  def debug(value: Boolean) = UnsafeSerial.debug(value)

}