blob: b985149be649ca25a8b00b0777e97b46a9adf9a9 [file] [log] [blame]
Brad Bishop613a5b32017-01-05 20:58:13 -05001/**
2 * Copyright © 2016 IBM Corporation
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 <cstdlib>
Brad Bishop08379a32017-03-06 21:28:46 -050017#include <experimental/filesystem>
Brad Bishop613a5b32017-01-05 20:58:13 -050018#include <memory>
Brad Bishop4db64422017-02-16 11:33:32 -050019#include <phosphor-logging/log.hpp>
Brad Bishop613a5b32017-01-05 20:58:13 -050020#include "sysfs.hpp"
21#include "util.hpp"
Brad Bishop613a5b32017-01-05 20:58:13 -050022
23std::string findHwmon(const std::string& ofNode)
24{
Brad Bishop08379a32017-03-06 21:28:46 -050025 namespace fs = std::experimental::filesystem;
Brad Bishop613a5b32017-01-05 20:58:13 -050026 static constexpr auto hwmonRoot = "/sys/class/hwmon";
Brad Bishop08379a32017-03-06 21:28:46 -050027 static constexpr auto ofRoot = "/sys/firmware/devicetree/base";
Brad Bishop613a5b32017-01-05 20:58:13 -050028
Brad Bishop08379a32017-03-06 21:28:46 -050029 fs::path fullOfPath{ofRoot};
30 fullOfPath /= ofNode;
Brad Bishop613a5b32017-01-05 20:58:13 -050031
Brad Bishop08379a32017-03-06 21:28:46 -050032 for (const auto& hwmonInst : fs::directory_iterator(hwmonRoot))
Brad Bishop613a5b32017-01-05 20:58:13 -050033 {
Brad Bishop08379a32017-03-06 21:28:46 -050034 auto path = hwmonInst.path();
35 path /= "of_node";
Brad Bishop613a5b32017-01-05 20:58:13 -050036
Brad Bishop08379a32017-03-06 21:28:46 -050037 if (fs::canonical(path) != fullOfPath)
Brad Bishop613a5b32017-01-05 20:58:13 -050038 {
39 continue;
40 }
41
Brad Bishop08379a32017-03-06 21:28:46 -050042 return hwmonInst.path();
Brad Bishop613a5b32017-01-05 20:58:13 -050043 }
44
45 return std::string();
46}
47
Brad Bishop4db64422017-02-16 11:33:32 -050048int readSysfsWithCallout(const std::string& root,
49 const std::string& instance,
50 const std::string& type,
51 const std::string& id,
52 const std::string& sensor)
53{
54 int value = 0;
55 std::string instancePath = root + '/' + instance;
56 std::string fullPath = make_sysfs_path(instancePath,
57 type, id, sensor);
58 std::ifstream ifs;
59
60 ifs.exceptions(std::ifstream::failbit
61 | std::ifstream::badbit
62 | std::ifstream::eofbit);
63 try
64 {
65 ifs.open(fullPath);
66 ifs >> value;
67 }
68 catch (const std::exception& e)
69 {
70 // Too many GCC bugs (53984, 66145) to do
71 // this the right way...
72 using Cleanup = phosphor::utility::Free<char>;
73
74 // errno should still reflect the error from the failing open
75 // or read system calls that got us here.
76 auto rc = errno;
77 std::string devicePath = instancePath + "/device";
78 auto real = std::unique_ptr<char, Cleanup>(
79 realpath(devicePath.c_str(), nullptr));
80 phosphor::logging::log<phosphor::logging::level::ERR>(
81 strerror(rc),
82 phosphor::logging::entry("CALLOUT_DEVICE_PATH=%s", real.get()),
83 phosphor::logging::entry("CALLOUT_ERRNO=%d", rc));
84 exit(EXIT_FAILURE);
85 }
86
87 return value;
88}
89
Brad Bishop613a5b32017-01-05 20:58:13 -050090// vim: tabstop=8 expandtab shiftwidth=4 softtabstop=4