Home | History | Annotate | Download | only in HidUtils
      1 /*
      2  * Copyright (C) 2017 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 #include "HidDefs.h"
     17 #include "HidLocal.h"
     18 #include "HidLog.h"
     19 #include <cstddef>
     20 
     21 namespace HidUtil {
     22 
     23 constexpr uint32_t INVALID_USAGE = 0xFFFF;
     24 constexpr uint32_t INVALID_DESIGNATOR = 0xFFFF;
     25 constexpr uint32_t INVALID_STRING = 0xFFFF;
     26 
     27 uint32_t HidLocal::getUsage(size_t index) const {
     28     if (usage.empty()) {
     29         return INVALID_USAGE;
     30     }
     31     return (index >= usage.size()) ? usage.back() : usage[index];
     32 }
     33 
     34 uint32_t HidLocal::getDesignator(size_t index) const {
     35     if (designator.empty()) {
     36         return INVALID_DESIGNATOR;
     37     }
     38     return (index >= designator.size()) ? designator.back() : designator[index];
     39 }
     40 
     41 uint32_t HidLocal::getString(size_t index) const {
     42     if (string.empty()) {
     43         return INVALID_STRING;
     44     }
     45     return (index >= string.size()) ? string.back() : string[index];
     46 }
     47 
     48 void HidLocal::clear() {
     49     *this = HidLocal();
     50 }
     51 
     52 bool HidLocal::append(const HidItem &i) {
     53     using namespace HidDef::LocalTag;
     54 
     55     bool ret = true;
     56     unsigned unsignedInteger;
     57     bool unsignedError = !i.dataAsUnsigned(&unsignedInteger);
     58     bool valueError = false;
     59 
     60     switch (i.tag) {
     61         case USAGE:
     62             usage.push_back(unsignedInteger);
     63             valueError = unsignedError;
     64             break;
     65         case USAGE_MINIMUM:
     66             usageMin = unsignedInteger;
     67             valueError = unsignedError;
     68             break;
     69         case USAGE_MAXIMUM:
     70             if (!usageMin.isSet()) {
     71                 LOG_E << "usage min not set when saw usage max " << i << LOG_ENDL;
     72                 ret = false;
     73             } else {
     74                 uint32_t usagemax = unsignedInteger;
     75                 valueError = unsignedError;
     76                 for (size_t j = usageMin.get(0); j <= usagemax; ++j) {
     77                     usage.push_back(j);
     78                 }
     79                 usageMin.clear();
     80             }
     81             break;
     82         case STRING_INDEX:
     83             string.push_back(unsignedInteger);
     84             valueError = unsignedError;
     85             break;
     86         case STRING_MINIMUM:
     87             stringMin = unsignedInteger;
     88             valueError = unsignedError;
     89             break;
     90         case STRING_MAXIMUM: {
     91             if (!usageMin.isSet()) {
     92                 LOG_E << "string min not set when saw string max " << i << LOG_ENDL;
     93                 ret = false;
     94             } else {
     95                 uint32_t stringMax = unsignedInteger;
     96                 valueError = unsignedError;
     97                 for (size_t j = stringMin.get(0); j <= stringMax; ++j) {
     98                     string.push_back(j);
     99                 }
    100                 stringMin.clear();
    101             }
    102             break;
    103         }
    104         case DELIMITOR:
    105             delimeter = unsignedInteger;
    106             valueError = unsignedError;
    107             break;
    108         default:
    109             LOG_E << "unknown local tag, " << i << LOG_ENDL;
    110             ret = false;
    111     }
    112     if (valueError) {
    113         LOG_E << "Cannot get unsigned data at " << i << LOG_ENDL;
    114         ret = false;
    115     }
    116     return ret;
    117 }
    118 } //namespace HidUtil
    119