+ if ((input_position + 8) >= sizeof(password))
+ return;
+
+ /* Whether the user currently holds down the shift key. */
+ bool shift = (event->state & XCB_MOD_MASK_SHIFT);
+
+ /* Whether Caps Lock (all lowercase alphabetic keys will be replaced by
+ * their uppercase variant) is active at the moment. */
+ bool capslock = (event->state & capslockmask);
+
+ /* Whether Shift Lock (shift state is reversed) is active at the moment. */
+ bool shiftlock = (event->state & shiftlockmask);
+
+ /* Whether Caps Lock or Shift Lock is active at the moment. */
+ bool lock = (capslock || shiftlock);
+
+ DEBUG("shift = %d, lock = %d, capslock = %d, shiftlock = %d\n",
+ shift, lock, capslock, shiftlock);
+
+ if ((event->state & numlockmask) && xcb_is_keypad_key(sym1)) {
+ /* this key was a keypad key */
+ if (shift || shiftlock)
+ sym = sym0;
+ else sym = sym1;
+ } else {
+ xcb_keysym_t upper, lower;
+ XConvertCase(sym0, (KeySym*)&lower, (KeySym*)&upper);
+ DEBUG("sym0 = %c (%d), sym1 = %c (%d), lower = %c (%d), upper = %c (%d)\n",
+ sym0, sym0, sym1, sym1, lower, lower, upper, upper);
+ /* If there is no difference between the uppercase and lowercase
+ * variant of this key, we consider Caps Lock off — it is only relevant
+ * for alphabetic keys, unlike Shift Lock. */
+ if (lower == upper) {
+ capslock = false;
+ lock = (capslock || shiftlock);
+ DEBUG("lower == upper, now shift = %d, lock = %d, capslock = %d, shiftlock = %d\n",
+ shift, lock, capslock, shiftlock);
+ }
+
+ /* In two different cases we need to use the uppercase keysym:
+ * 1) The user holds shift, no lock is active.
+ * 2) Any of the two locks is active.
+ */
+ if ((shift && !lock) || (!shift && lock))
+ sym = sym1;
+ else sym = sym0;
+ }
+