⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 keyboard.c

📁 早期freebsd实现
💻 C
📖 第 1 页 / 共 4 页
字号:
#ifdef subprocesses	  wait_reading_process_input (0, -1, 1);#else/* Note SIGIO has been undef'd if FIONREAD is missing.  */#ifdef SIGIO	  if (interrupt_input)	    {	      sigblockx (SIGIO);	      set_waiting_for_input (0);	      while (!kbd_count)		sigpausex (SIGIO);	      clear_waiting_for_input ();	      sigunblockx (SIGIO);	    }#else	  interrupt_input = 0;#endif /* not SIGIO */#endif /* subprocesses */	  if (!interrupt_input && !kbd_count)	    {	      read_avail_input (0);	    }	}#endif /* not VMS */    }  input_pending = --kbd_count > 0;  c = *kbd_ptr;			/* *kbd_ptr++ would have a timing error. */  kbd_ptr++;			/* See kbd_buffer_store_char. */  return (c & (meta_key ? 0377 : 0177)); /* Clean up if sign was extended. */}/* Force an attempt to read input regardless of what FIONREAD says.  */force_input_read (){  force_input = 1;  detect_input_pending ();  force_input = 0;}/* Store into *addr the number of terminal input chars available.   Equivalent to ioctl (0, FIONREAD, addr) but works   even if FIONREAD does not exist.  */static voidget_input_pending (addr)     int *addr;{#ifdef VMS  /* On VMS, we always have something in the buffer     if any input is available.  */  /*** It might be simpler to make interrupt_input 1 on VMS ***/  *addr = kbd_count | !NULL (Vquit_flag);#else  /* First of all, have we already counted some input?  */  *addr = kbd_count | !NULL (Vquit_flag);  /* If input is being read as it arrives, and we have none, there is none.  */  if (*addr > 0 || (interrupt_input && ! interrupts_deferred && ! force_input))    return;#ifdef FIONREAD  if (! force_input)    {      /* If we can count the input without reading it, do so.  */      if (ioctl (0, FIONREAD, addr) < 0)	*addr = 0;      if (*addr == 0 || read_socket_hook == 0)	return;      /* If the input consists of window-events, not all of them	 are necessarily kbd chars.  So process all the input	 and see how many kbd chars we got.  */    }#endif#ifdef SIGIO  {    /* It seems there is a timing error such that a SIGIO can be handled here       and cause kbd_count to become nonzero even though raising of SIGIO       has already been turned off.  */    int mask = sigblock (sigmask (SIGIO));    if (kbd_count == 0)      read_avail_input (*addr);    sigsetmask (mask);  }#else  /* If we can't count the input, read it (if any) and see what we got.  */  read_avail_input (*addr);#endif  *addr = kbd_count | !NULL (Vquit_flag);#endif}/* Read pending any input out of the system and into Emacs.  *//* This function is temporary in Emacs 18.  It is used only   with X windows.  X windows always turns on interrupt input   if possible, so this function has nothing to do except   on systems that don't have SIGIO.  And they also don't have FIONREAD.  */voidconsume_available_input (){#ifdef SIGIO  if (!interrupt_input || interrupts_deferred)#endif    read_avail_input (0);}/* Read any terminal input already buffered up by the system   into the kbd_buffer, assuming the buffer is currently empty.   Never waits.   If NREAD is nonzero, assume it contains # chars of raw data waiting.   If it is zero, we determine that datum.   Input gets into the kbd_buffer either through this function   (at main program level) or at interrupt level if input   is interrupt-driven.  */static voidread_avail_input (nread)     int nread;{  /* This function is not used on VMS.  */#ifndef VMS  char buf[256 * BUFFER_SIZE_FACTOR];  register int i;#ifdef FIONREAD  if (! force_input)    {      if (nread == 0)	get_input_pending (&nread);      if (nread == 0)	return;    }  if (nread > sizeof buf)    nread = sizeof buf;  /* Read what is waiting.  */  if (read_socket_hook)    nread = (*read_socket_hook) (0, buf, nread);  else    nread = read (0, buf, nread);#else /* no FIONREAD */#ifdef USG  fcntl (fileno (stdin), F_SETFL, O_NDELAY);  if (read_socket_hook)    {      nread = (*read_socket_hook) (0, buf, sizeof buf);    }  else    {      nread = read (fileno (stdin), buf, sizeof buf);    }#ifdef EBADSLT  if (nread == -1 && (errno == EAGAIN || errno == EBADSLT))#else  if (nread == -1 && errno == EAGAIN)#endif    nread = 0;  fcntl (fileno (stdin), F_SETFL, 0);#else /* not USG */  you lose#endif /* not USG */#endif /* no FIONREAD */  /* Scan the chars for C-g and store them in kbd_buffer.  */  if (kbd_count == 0)    kbd_ptr = kbd_buffer;  for (i = 0; i < nread; i++)    {      kbd_buffer_store_char (buf[i]);      /* Don't look at input that follows a C-g too closely.	 This reduces lossage due to autorepeat on C-g.  */      if (buf[i] == quit_char)	break;    }#endif /* not VMS */}#ifdef SIGIO   /* for entire page *//* Note SIGIO has been undef'd if FIONREAD is missing.  *//* If using interrupt input and some input chars snuck into the   buffer before we enabled interrupts, fake an interrupt for them.  */gobble_input (){  int nread;  if (interrupt_input)    {      if (ioctl (0, FIONREAD, &nread) < 0)	nread = 0;      if (nread)	{	  sigholdx (SIGIO);	  input_available_signal (SIGIO);	  sigfree ();	}    }}input_available_signal (signo)     int signo;{  unsigned char buf[256 * BUFFER_SIZE_FACTOR];  int nread;  register int i;  /* Must preserve main program's value of errno.  */  int old_errno = errno;#ifdef BSD4_1  extern int select_alarmed;#endif#ifdef USG  /* USG systems forget handlers when they are used;     must reestablish each time */  signal (signo, input_available_signal);#endif /* USG */#ifdef BSD4_1  sigisheld (SIGIO);#endif  if (input_available_clear_word)    *input_available_clear_word = 0;  while (1)    {      if (ioctl (0, FIONREAD, &nread) < 0)	/* Formerly simply exited the loop, but that sometimes led to	   a failure of Emacs to terminate.	   SIGHUP seems appropriate if we can't reach the terminal.  */	kill (getpid (), SIGHUP);      if (nread <= 0)	break;#ifdef BSD4_1      select_alarmed = 1;  /* Force the select emulator back to life */#endif      if (read_socket_hook)	{	  nread = (*read_socket_hook) (0, buf, sizeof buf);	  if (!nread)	    continue;	}      else	{	  if (nread > sizeof buf)	    nread = sizeof buf;	  nread = read (0, buf, nread);	}      for (i = 0; i < nread; i++)	{	  kbd_buffer_store_char (buf[i]);	  /* Don't look at input that follows a C-g too closely.	     This reduces lossage due to autorepeat on C-g.  */	  if (buf[i] == quit_char)	    break;	}    }#ifdef BSD4_1  sigfree ();#endif  errno = old_errno;}#endif /* SIGIO */#if 0/* This is turned off because it didn't produce much speedup.  *//* Read a single-char key sequence.  Do not redisplay.   Return 1 if successful, or 0 if what follows is not   a single-char key.  (In that case, a char has been unread.)   This is used instead of read_key_sequence as an optimization   just after a direct-updating command is done, since at such   times we know that no redisplay is required.  */intfast_read_one_key (keybuf)     char *keybuf;{  register Lisp_Object map;  register int c;  register Lisp_Object tem;  keys_prompt = 0;  /* Read a character, and do not redisplay.  */  c = read_command_char (-1);  Vquit_flag = Qnil;  /* Assume until further notice that we are unlucky     and will return zero, so this char will be     reread by read_key_sequence.  */  unread_command_char = c;  if (c < 0 || c >= 0200)    return 0;  map = current_buffer->keymap;  if (!EQ (map, Qnil))    {      tem = get_keyelt (access_keymap (map, c));      if (!EQ (tem, Qnil))	return 0;    }  XSET (map, Lisp_Vector, global_map);  tem = !NULL (map)    ? get_keyelt (access_keymap (map, c))      : Qnil;  read_key_sequence_cmd = tem;  /* trace symbols to their function definitions */  while (XTYPE (tem) == Lisp_Symbol && !NULL (tem)	 && !EQ (tem, Qunbound))    tem = XSYMBOL (tem)->function;  /* Is the definition a prefix character?  */  if (XTYPE (tem) == Lisp_Vector ||      (CONSP (tem) && EQ (XCONS (tem)->car, Qkeymap)))    return 0;  unread_command_char = -1;  keybuf[0] = c;  return 1;}#endif /* 0 *//* Read a sequence of keys that ends with a non prefix character, and store them in KEYBUF, a buffer of size BUFSIZE. Prompt with PROMPT.  Echo starting immediately unless `prompt' is 0. Return the length of the key sequence stored. NODISPLAY nonzero means don't do redisplay before the first character (just for speedup).  */intread_key_sequence (keybuf, bufsize, prompt, nodisplay)     char *keybuf;     int bufsize;     unsigned char *prompt;     int nodisplay;{  register int i;  Lisp_Object nextlocal, nextglobal;  register int c, nextc;  Lisp_Object local, global;  if (FROM_KBD)    {      if (prompt)	echo_prompt (prompt);      else if (cursor_in_echo_area)	echo_dash ();    }  nextc = read_command_char (nodisplay ? -1 : !prompt);  nextlocal = current_buffer->keymap;  XSET (nextglobal, Lisp_Vector, global_map);  i = 0;  while (!NULL (nextlocal) || !NULL (nextglobal))    {      if (i == bufsize)	error ("key sequence too long");      if (nextc >= 0)	{	  c = nextc;	  nextc = -1;	}      else	c = read_command_char (!prompt);      Vquit_flag = Qnil;      nodisplay = 0;      if (c < 0)	return 0;      if (c >= 0200)	{	  nextc = c & 0177;	  c = meta_prefix_char;	}      keybuf[i] = c;      global = !NULL (nextglobal)	? get_keyelt (access_keymap (nextglobal, c))	  : Qnil;      local = !NULL (nextlocal)	? get_keyelt (access_keymap (nextlocal, c))	  : Qnil;      /* If C is not defined in either keymap	 and it is an uppercase letter, try corresponding lowercase.  */      if (NULL (global) && NULL (local) && UPPERCASEP (c))	{	  global = !NULL (nextglobal)	    ? get_keyelt (access_keymap (nextglobal, DOWNCASE (c)))	      : Qnil;	  local = !NULL (nextlocal)	    ? get_keyelt (access_keymap (nextlocal, DOWNCASE (c)))	      : Qnil;	  /* If that has worked better that the original char,	     downcase it permanently.  */	  if (!NULL (global) || !NULL (local))	    {	      keybuf[i] = c = DOWNCASE (c);	    }	}      i++;      nextlocal = Qnil;      nextglobal = Qnil;      read_key_sequence_cmd = !NULL (local) ? local : global;      /* trace symbols to their function definitions */      while (XTYPE (global) == Lisp_Symbol && !NULL (global)	     && !EQ (global, Qunbound))	global = XSYMBOL (global)->function;      while (XTYPE (local) == Lisp_Symbol && !NULL (local)	     && !EQ (local, Qunbound))	local = XSYMBOL (local)->function;      /* Are the definitions prefix characters? */      if (XTYPE (local) == Lisp_Vector ||	  (CONSP (local) && EQ (XCONS (local)->car, Qkeymap))	  ||	  /* If nextc is set, we are processing a prefix char	     that represents a meta-bit.	     Let a global prefix definition override a local non-prefix.	     This is for minibuffers that redefine Escape for completion.	     A real Escape gets completion, but Meta bits get ESC-prefix.  */	  ((NULL (local) || nextc >= 0)	   && (XTYPE (global) == Lisp_Vector ||	       (CONSP (global) && EQ (XCONS (global)->car, Qkeymap)))))	{	  if (XTYPE (local) == Lisp_Vector ||	      (CONSP (local) && EQ (XCONS (local)->car, Qkeymap)))	    nextlocal = local;	  else	    nextlocal = Qnil;	  if (XTYPE (global) == Lisp_Vector ||	      (CONSP (global) && EQ (XCONS (global)->car, Qkeymap)))	    nextglobal = global;	  else	    nextglobal = Qnil;	}    }  return i;}DEFUN ("read-key-sequence", Fread_key_sequence, Sread_key_sequence, 1, 1, 0,  "Read a sequence of keystrokes and return as a string.\n\The sequence is sufficient to specify a non-prefix command\n\starting from the current local and global keymaps.\n\A C-g typed while in this function is treated like\n\any other character, and quit-flag is not set.\n\One arg, PROMPT, a prompt string or  nil, meaning do not prompt specially.")  (prompt)     Lisp_Object prompt;{  char keybuf[30];  register int i;  if (!NULL (prompt))    CHECK_STRING (prompt, 0);  QUIT;  this_command_key_count = 0;  i = read_key_sequence (keybuf, sizeof keybuf,			 (NULL (prompt)) ? 0 : XSTRING (prompt)->data,			 0);  return make_string (keybuf, i);}DEFUN ("command-execute", Fcommand_execute, Scommand_execute, 1, 2, 0, "Execute CMD as an editor command.\n\CMD must be a symbol that satisfies the `commandp' predicate.\n\Optional second arg RECORD-FLAG non-nil\n\means unconditionally put this command in the command-history.\n\Otherwise, this is done only if an arg is read using the minibuffer.")     (cmd, record)     Lisp_Object cmd, record;{  register Lisp_Object final;  register Lisp_Object tem;  Lisp_Object prefixarg;  struct backtrace backtrace;  extern int debug_on_next_call;  prefixarg = Vprefix_arg, Vprefix_arg = Qnil;  Vcurrent_prefix_arg = prefixarg;  debug_on_next_call = 0;  if (XTYPE (cmd) == Lisp_Symbol)    {      tem = Fget (cmd, Qdisabled);      if (!NULL (tem))	return call0 (Vdisabled_command_hook);    }  while (1)    {      final = cmd;      while (XTYPE (final) == Lisp_Symbol)	{	  if (EQ (Qunbound, XSYMBOL (final)->function))	    Fsymbol_function (final);    /* Get an error! */	  final = XSYMBOL (final)->function;	}      if (CONSP (final) && (tem = Fcar (final), EQ (tem, Qautoload)))	do_autoload (final, cmd);      else	break;    }  if (CONSP (final) || XTYPE (final) == Lisp_Subr)    {      backtrace.next = backtrace_list;      backtrace_list = &backtrace;      backtrace.function = &Qcall_interactively;      backtrace.args = &cmd;      backtrace.nargs = 1;      backtrace.evalargs = 0;      tem = Fcall_interactively (cmd, record);      backtrace_list = backtrace.next;      return tem;    }  if (XTYPE (final) == Lisp_String)    {      return Fexecute_kbd_macro (final, prefixarg);    }  return Qnil;}DEFUN ("execute-extended-command", Fexecute_extended_command, Sexecute_extended_command,  1, 1, "P",  "Read function name, then read its arguments and call it.")  (prefixarg)     Lisp_Object prefixarg;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -