Subversion Repositories HelenOS

Rev

Go to most recent revision | Blame | Last modification | View Log | Download | RSS feed

  1. /*
  2.  * Copyright (c) 2009 Jakub Jermar
  3.  * All rights reserved.
  4.  *
  5.  * Redistribution and use in source and binary forms, with or without
  6.  * modification, are permitted provided that the following conditions
  7.  * are met:
  8.  *
  9.  * - Redistributions of source code must retain the above copyright
  10.  *   notice, this list of conditions and the following disclaimer.
  11.  * - Redistributions in binary form must reproduce the above copyright
  12.  *   notice, this list of conditions and the following disclaimer in the
  13.  *   documentation and/or other materials provided with the distribution.
  14.  * - The name of the author may not be used to endorse or promote products
  15.  *   derived from this software without specific prior written permission.
  16.  *
  17.  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
  18.  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  19.  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
  20.  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
  21.  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
  22.  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
  23.  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
  24.  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  25.  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  26.  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  27.  */
  28.  
  29. /** @addtogroup genarch
  30.  * @{
  31.  */
  32. /**
  33.  * @file
  34.  * @brief Serial line processing.
  35.  */
  36.  
  37. #include <genarch/srln/srln.h>
  38. #include <console/chardev.h>
  39. #include <console/console.h>
  40. #include <proc/thread.h>
  41. #include <arch.h>
  42. #include <string.h>
  43.  
  44. static indev_operations_t srln_raw_ops = {
  45.     .poll = NULL
  46. };
  47.  
  48. static void ksrln(void *arg)
  49. {
  50.     srln_instance_t *instance = (srln_instance_t *) arg;
  51.     bool cr = false;
  52.     uint32_t escape = 0;
  53.    
  54.     while (true) {
  55.         wchar_t ch = indev_pop_character(&instance->raw);
  56.        
  57.         /* ANSI escape sequence processing */
  58.         if (escape != 0) {
  59.             escape <<= 8;
  60.             escape |= ch & 0xff;
  61.            
  62.             if ((escape == 0x1b4f) || (escape == 0x1b5b) || (escape == 0x1b5b33))
  63.                 continue;
  64.            
  65.             switch (escape) {
  66.             case 0x1b4f46:
  67.             case 0x1b5b46:
  68.                 ch = U_END_ARROW;
  69.                 escape = 0;
  70.                 break;
  71.             case 0x1b4f48:
  72.             case 0x1b5b48:
  73.                 ch = U_HOME_ARROW;
  74.                 escape = 0;
  75.                 break;
  76.             case 0x1b5b41:
  77.                 ch = U_UP_ARROW;
  78.                 escape = 0;
  79.                 break;
  80.             case 0x1b5b42:
  81.                 ch = U_DOWN_ARROW;
  82.                 escape = 0;
  83.                 break;
  84.             case 0x1b5b43:
  85.                 ch = U_RIGHT_ARROW;
  86.                 escape = 0;
  87.                 break;
  88.             case 0x1b5b44:
  89.                 ch = U_LEFT_ARROW;
  90.                 escape = 0;
  91.                 break;
  92.             case 0x1b5b337e:
  93.                 ch = U_DELETE;
  94.                 escape = 0;
  95.                 break;
  96.             default:
  97.                 escape = 0;
  98.             }
  99.         }
  100.        
  101.         if (ch == 0x1b) {
  102.             escape = ch & 0xff;
  103.             continue;
  104.         }
  105.        
  106.         /* Replace carriage return with line feed
  107.            and suppress any following line feed */
  108.         if ((ch == '\n') && (cr)) {
  109.             cr = false;
  110.             continue;
  111.         }
  112.        
  113.         if (ch == '\r') {
  114.             ch = '\n';
  115.             cr = true;
  116.         } else
  117.             cr = false;
  118.        
  119.         /* Backspace */
  120.         if (ch == 0x7f)
  121.             ch = '\b';
  122.        
  123.         indev_push_character(instance->sink, ch);
  124.     }
  125. }
  126.  
  127. srln_instance_t *srln_init(void)
  128. {
  129.     srln_instance_t *instance
  130.         = malloc(sizeof(srln_instance_t), FRAME_ATOMIC);
  131.     if (instance) {
  132.         instance->thread
  133.             = thread_create(ksrln, (void *) instance, TASK, 0, "ksrln", false);
  134.        
  135.         if (!instance->thread) {
  136.             free(instance);
  137.             return NULL;
  138.         }
  139.        
  140.         instance->sink = NULL;
  141.         indev_initialize("srln", &instance->raw, &srln_raw_ops);
  142.     }
  143.    
  144.     return instance;
  145. }
  146.  
  147. indev_t *srln_wire(srln_instance_t *instance, indev_t *sink)
  148. {
  149.     ASSERT(instance);
  150.     ASSERT(sink);
  151.    
  152.     instance->sink = sink;
  153.     thread_ready(instance->thread);
  154.    
  155.     return &instance->raw;
  156. }
  157.  
  158. /** @}
  159.  */
  160.