2007-09-04 00:11:15 +08:00
|
|
|
/*
|
|
|
|
* Copyright (C) [2004, 2005, 2006], Hyperic, Inc.
|
|
|
|
* This file is part of SIGAR.
|
|
|
|
*
|
|
|
|
* SIGAR is free software; you can redistribute it and/or modify
|
|
|
|
* it under the terms version 2 of the GNU General Public License as
|
|
|
|
* published by the Free Software Foundation. This program is distributed
|
|
|
|
* in the hope that it will be useful, but WITHOUT ANY WARRANTY; without
|
|
|
|
* even the implied warranty of MERCHANTABILITY or FITNESS FOR A
|
|
|
|
* PARTICULAR PURPOSE. See the GNU General Public License for more
|
|
|
|
* details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU General Public License
|
|
|
|
* along with this program; if not, write to the Free Software
|
|
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
|
|
* USA.
|
|
|
|
*/
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
#include <ruby.h>
|
2009-03-26 11:10:19 +08:00
|
|
|
#ifdef RB_RUBY_19
|
|
|
|
#include <ruby/re.h>
|
|
|
|
#else
|
|
|
|
#include <re.h>
|
|
|
|
#endif
|
|
|
|
|
2007-09-24 10:35:35 +08:00
|
|
|
#include <errno.h>
|
2007-09-03 08:49:22 +08:00
|
|
|
#include "sigar.h"
|
|
|
|
#include "sigar_fileinfo.h"
|
2009-07-29 13:38:38 +08:00
|
|
|
#include "sigar_log.h"
|
2007-09-03 08:49:22 +08:00
|
|
|
#include "sigar_format.h"
|
2009-03-16 03:33:54 +08:00
|
|
|
#include "sigar_ptql.h"
|
2007-09-03 08:49:22 +08:00
|
|
|
|
2009-03-16 03:33:54 +08:00
|
|
|
#define RB_SIGAR_RAISE(msg) rb_raise(rb_eArgError, "%s", msg)
|
|
|
|
#define RB_SIGAR_CROAK RB_SIGAR_RAISE(sigar_strerror(sigar, status))
|
2009-07-29 13:38:38 +08:00
|
|
|
#define OBJ2PID(pid) rb_sigar_pid_get(rbsigar, pid)
|
2007-09-03 08:49:22 +08:00
|
|
|
|
2009-02-16 11:51:40 +08:00
|
|
|
#ifndef RSTRING_PTR
|
2009-02-16 12:09:42 +08:00
|
|
|
#define RSTRING_PTR(s) RSTRING(s)->ptr
|
2009-02-16 11:51:40 +08:00
|
|
|
#endif
|
|
|
|
|
|
|
|
#ifndef RSTRING_LEN
|
2009-02-16 12:09:42 +08:00
|
|
|
#define RSTRING_LEN(s) RSTRING(s)->len
|
2009-02-16 11:51:40 +08:00
|
|
|
#endif
|
|
|
|
|
2009-03-26 11:10:19 +08:00
|
|
|
#ifdef RB_HAS_RE_ERROR
|
2009-03-26 05:58:06 +08:00
|
|
|
# define RB_REGEX_ERROR rb_eRegexpError
|
|
|
|
#else
|
|
|
|
# define RB_REGEX_ERROR rb_eArgError
|
|
|
|
#endif
|
|
|
|
|
2009-07-29 13:38:38 +08:00
|
|
|
#define SIGAR \
|
|
|
|
sigar_t *sigar = rbsigar->sigar;
|
|
|
|
|
|
|
|
#define SIGAR_GET \
|
|
|
|
rb_sigar_t *rbsigar = rb_sigar_get(obj); \
|
|
|
|
SIGAR;
|
|
|
|
|
|
|
|
typedef struct {
|
2007-09-03 08:49:22 +08:00
|
|
|
sigar_t *sigar;
|
2009-07-29 13:38:38 +08:00
|
|
|
VALUE logger;
|
|
|
|
} rb_sigar_t;
|
|
|
|
|
|
|
|
static rb_sigar_t *rb_sigar_get(VALUE obj)
|
|
|
|
{
|
|
|
|
rb_sigar_t *rbsigar;
|
|
|
|
Data_Get_Struct(obj, rb_sigar_t, rbsigar);
|
|
|
|
return rbsigar;
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2009-03-17 11:04:33 +08:00
|
|
|
static int rbsigar_ptql_re_impl(void *data,
|
|
|
|
char *haystack, char *needle)
|
|
|
|
{
|
2009-03-26 11:10:19 +08:00
|
|
|
#ifdef RB_RUBY_19
|
|
|
|
/* XXX no more regex.h */
|
|
|
|
return 0;
|
|
|
|
#else
|
2009-03-17 11:04:33 +08:00
|
|
|
struct re_pattern_buffer *regex;
|
|
|
|
int len = strlen(haystack);
|
|
|
|
int retval;
|
|
|
|
const char *err;
|
|
|
|
|
|
|
|
regex = ALLOC(struct re_pattern_buffer);
|
|
|
|
MEMZERO((char *)regex, struct re_pattern_buffer, 1);
|
|
|
|
/* XXX cache */
|
|
|
|
if ((err = re_compile_pattern(needle, strlen(needle), regex))) {
|
|
|
|
re_free_pattern(regex);
|
2009-03-26 05:58:06 +08:00
|
|
|
rb_raise(RB_REGEX_ERROR, "%s", err);
|
2009-03-17 11:04:33 +08:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
|
|
|
retval = re_match(regex, haystack, len, 0, NULL);
|
|
|
|
re_free_pattern(regex);
|
|
|
|
return retval > 0;
|
2009-03-26 11:10:19 +08:00
|
|
|
#endif
|
2009-03-17 11:04:33 +08:00
|
|
|
}
|
|
|
|
|
2009-03-16 03:33:54 +08:00
|
|
|
#define sigar_isdigit(c) \
|
|
|
|
(isdigit(((unsigned char)(c))))
|
|
|
|
|
2009-07-29 13:38:38 +08:00
|
|
|
static sigar_pid_t rb_sigar_pid_get(rb_sigar_t *rbsigar, VALUE obj)
|
2009-03-16 03:33:54 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR;
|
|
|
|
|
2009-03-16 03:33:54 +08:00
|
|
|
if (TYPE(obj) == T_STRING) {
|
|
|
|
char *pid = StringValuePtr(obj);
|
|
|
|
|
|
|
|
if (sigar_isdigit(*pid)) {
|
|
|
|
obj = rb_str2inum(obj, 10);
|
|
|
|
/* fallthru */
|
|
|
|
}
|
|
|
|
else if ((RSTRING_LEN(obj) == 2) &&
|
|
|
|
(*pid == '$') && (*(pid + 1) == '$'))
|
|
|
|
{
|
|
|
|
return sigar_pid_get(sigar);
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
/* XXX cache queries */
|
|
|
|
sigar_ptql_query_t *query;
|
|
|
|
sigar_ptql_error_t error;
|
|
|
|
int status =
|
|
|
|
sigar_ptql_query_create(&query, (char *)pid, &error);
|
|
|
|
|
|
|
|
if (status == SIGAR_OK) {
|
|
|
|
sigar_pid_t qpid;
|
|
|
|
|
2009-03-17 11:04:33 +08:00
|
|
|
sigar_ptql_re_impl_set(sigar, NULL, rbsigar_ptql_re_impl);
|
2009-03-16 03:33:54 +08:00
|
|
|
status = sigar_ptql_query_find_process(sigar, query, &qpid);
|
2009-03-17 11:04:33 +08:00
|
|
|
sigar_ptql_re_impl_set(sigar, NULL, NULL);
|
2009-03-16 03:33:54 +08:00
|
|
|
sigar_ptql_query_destroy(query);
|
|
|
|
if (status == SIGAR_OK) {
|
|
|
|
return qpid;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
RB_SIGAR_RAISE(sigar_strerror(sigar, status));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
RB_SIGAR_RAISE(error.message);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return NUM2UINT(obj);
|
|
|
|
}
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
static void rb_sigar_free(void *obj)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
xfree(obj);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void rb_sigar_close(rb_sigar_t *rbsigar)
|
|
|
|
{
|
|
|
|
sigar_close(rbsigar->sigar);
|
|
|
|
rb_sigar_free(rbsigar);
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2009-07-29 13:38:38 +08:00
|
|
|
static void rb_sigar_mark(rb_sigar_t *rbsigar)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
rb_gc_mark(rbsigar->logger);
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_new(VALUE module)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
rb_sigar_t *rbsigar;
|
|
|
|
rbsigar = ALLOC(rb_sigar_t);
|
|
|
|
sigar_open(&(rbsigar->sigar));
|
|
|
|
return Data_Wrap_Struct(module, rb_sigar_mark, rb_sigar_close, rbsigar);
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2007-09-03 09:57:02 +08:00
|
|
|
static VALUE rb_sigar_format_size(VALUE rclass, VALUE size)
|
|
|
|
{
|
|
|
|
char buffer[56];
|
|
|
|
return rb_str_new2(sigar_format_size(NUM2LL(size), buffer));
|
|
|
|
}
|
|
|
|
|
2007-09-03 11:13:41 +08:00
|
|
|
static VALUE rb_sigar_net_interface_flags_to_s(VALUE rclass, VALUE flags)
|
|
|
|
{
|
|
|
|
char buffer[1024];
|
|
|
|
return rb_str_new2(sigar_net_interface_flags_to_string(NUM2LL(flags), buffer));
|
|
|
|
}
|
|
|
|
|
2007-09-23 09:47:26 +08:00
|
|
|
static VALUE rb_sigar_net_connection_type_to_s(VALUE rclass, VALUE type)
|
|
|
|
{
|
|
|
|
return rb_str_new2(sigar_net_connection_type_get(NUM2INT(type)));
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_net_connection_state_to_s(VALUE rclass, VALUE state)
|
|
|
|
{
|
|
|
|
return rb_str_new2(sigar_net_connection_state_get(NUM2INT(state)));
|
|
|
|
}
|
|
|
|
|
2007-09-10 01:21:45 +08:00
|
|
|
static VALUE rb_sigar_net_address_to_string(sigar_net_address_t *address)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
|
|
|
char addr_str[SIGAR_INET6_ADDRSTRLEN];
|
2007-09-10 01:21:45 +08:00
|
|
|
sigar_net_address_to_string(NULL, address, addr_str);
|
2007-09-03 08:49:22 +08:00
|
|
|
return rb_str_new2(addr_str);
|
|
|
|
}
|
|
|
|
|
2009-07-30 07:08:16 +08:00
|
|
|
static VALUE rb_sigar_net_scope_to_s(VALUE rclass, VALUE type)
|
|
|
|
{
|
|
|
|
return rb_str_new2(sigar_net_scope_to_string(NUM2INT(type)));
|
|
|
|
}
|
|
|
|
|
2007-09-10 01:21:45 +08:00
|
|
|
#define rb_sigar_net_address_to_s(a) rb_sigar_net_address_to_string(&a)
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
static VALUE rb_sigar_new_list(char *data, unsigned long number,
|
|
|
|
int size, VALUE rclass)
|
|
|
|
{
|
|
|
|
unsigned long i;
|
|
|
|
VALUE av = rb_ary_new2(number);
|
|
|
|
|
|
|
|
for (i=0; i<number; i++, data += size) {
|
|
|
|
void *ent = malloc(size);
|
|
|
|
|
|
|
|
memcpy(ent, data, size);
|
|
|
|
rb_ary_push(av, Data_Wrap_Struct(rclass, 0, free, ent));
|
|
|
|
}
|
|
|
|
|
|
|
|
return av;
|
|
|
|
}
|
|
|
|
|
2007-09-03 10:42:41 +08:00
|
|
|
static VALUE rb_sigar_new_strlist(char **data, unsigned long number)
|
|
|
|
{
|
|
|
|
unsigned long i;
|
|
|
|
VALUE av = rb_ary_new2(number);
|
|
|
|
|
|
|
|
for (i=0; i<number; i++) {
|
|
|
|
rb_ary_push(av, rb_str_new2(data[i]));
|
|
|
|
}
|
|
|
|
|
|
|
|
return av;
|
|
|
|
}
|
|
|
|
|
2007-09-24 07:48:29 +08:00
|
|
|
static VALUE rb_sigar_new_intlist(int *data, int number)
|
|
|
|
{
|
|
|
|
int i;
|
|
|
|
VALUE av = rb_ary_new2(number);
|
|
|
|
|
|
|
|
for (i=0; i<number; i++) {
|
|
|
|
rb_ary_push(av, rb_int2inum(data[i]));
|
|
|
|
}
|
|
|
|
|
|
|
|
return av;
|
|
|
|
}
|
|
|
|
|
2007-09-03 10:42:41 +08:00
|
|
|
static VALUE rb_sigar_net_interface_list(VALUE obj)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-03 10:42:41 +08:00
|
|
|
int status;
|
|
|
|
sigar_net_interface_list_t iflist;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_net_interface_list_get(sigar, &iflist);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_strlist(iflist.data, iflist.number);
|
|
|
|
|
|
|
|
sigar_net_interface_list_destroy(sigar, &iflist);
|
|
|
|
|
|
|
|
return RETVAL;
|
|
|
|
}
|
|
|
|
|
2007-09-24 10:35:35 +08:00
|
|
|
static int rb_sigar_str2net_address(VALUE bytes, sigar_net_address_t *address)
|
|
|
|
{
|
2009-02-16 11:51:40 +08:00
|
|
|
long len = RSTRING_LEN(bytes);
|
2007-09-24 10:35:35 +08:00
|
|
|
|
|
|
|
switch (len) {
|
|
|
|
case 4:
|
|
|
|
address->family = SIGAR_AF_INET;
|
|
|
|
break;
|
|
|
|
case 4*4:
|
|
|
|
address->family = SIGAR_AF_INET6;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
return EINVAL;
|
|
|
|
}
|
|
|
|
|
2009-02-16 11:51:40 +08:00
|
|
|
memcpy(RSTRING_PTR(bytes), &address->addr.in6, len);
|
2007-09-24 10:35:35 +08:00
|
|
|
|
|
|
|
return SIGAR_OK;
|
|
|
|
}
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
static VALUE rb_cSigarNetStat;
|
|
|
|
|
2007-09-24 10:35:35 +08:00
|
|
|
static VALUE rb_sigar_net_stat_get(VALUE obj, VALUE flags, VALUE bytes, int port)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-24 07:48:29 +08:00
|
|
|
int status;
|
|
|
|
int has_port = (port != -1);
|
|
|
|
sigar_net_stat_t *RETVAL = malloc(sizeof(*RETVAL));
|
2007-09-24 10:35:35 +08:00
|
|
|
sigar_net_address_t address;
|
2007-09-24 07:48:29 +08:00
|
|
|
|
|
|
|
if (has_port) {
|
2007-09-24 10:35:35 +08:00
|
|
|
status = rb_sigar_str2net_address(bytes, &address);
|
|
|
|
if (status == SIGAR_OK) {
|
|
|
|
status = sigar_net_stat_port_get(sigar, RETVAL, NUM2INT(flags),
|
|
|
|
&address, port);
|
|
|
|
}
|
2007-09-24 07:48:29 +08:00
|
|
|
}
|
|
|
|
else {
|
|
|
|
status = sigar_net_stat_get(sigar, RETVAL, NUM2INT(flags));
|
|
|
|
}
|
|
|
|
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
free(RETVAL);
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
return Data_Wrap_Struct(rb_cSigarNetStat, 0, rb_sigar_free, RETVAL);
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_net_stat(VALUE obj, VALUE flags)
|
|
|
|
{
|
|
|
|
return rb_sigar_net_stat_get(obj, flags, Qnil, -1);
|
|
|
|
}
|
|
|
|
|
2007-09-24 10:35:35 +08:00
|
|
|
static VALUE rb_sigar_net_stat_port(VALUE obj, VALUE flags, VALUE address, VALUE port)
|
|
|
|
{
|
|
|
|
return rb_sigar_net_stat_get(obj, flags, address, NUM2INT(port));
|
|
|
|
}
|
|
|
|
|
2007-09-24 07:48:29 +08:00
|
|
|
static VALUE rb_sigar_NetStat_tcp_states(VALUE self)
|
|
|
|
{
|
|
|
|
sigar_net_stat_t *net_stat;
|
|
|
|
|
|
|
|
Data_Get_Struct(self, sigar_net_stat_t, net_stat);
|
|
|
|
|
|
|
|
return rb_sigar_new_intlist(&net_stat->tcp_states[0], SIGAR_TCP_UNKNOWN);
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_cSigarNetConnection;
|
|
|
|
|
2007-09-16 05:54:03 +08:00
|
|
|
static VALUE rb_sigar_net_connection_list(VALUE obj, VALUE flags)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-16 05:54:03 +08:00
|
|
|
int status;
|
|
|
|
sigar_net_connection_list_t connlist;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_net_connection_list_get(sigar, &connlist, NUM2UINT(flags));
|
|
|
|
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_list((char *)&connlist.data[0],
|
|
|
|
connlist.number,
|
|
|
|
sizeof(*connlist.data),
|
|
|
|
rb_cSigarNetConnection);
|
|
|
|
|
|
|
|
sigar_net_connection_list_destroy(sigar, &connlist);
|
|
|
|
|
|
|
|
return RETVAL;
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2007-09-23 09:47:26 +08:00
|
|
|
static VALUE rb_sigar_net_services_name(VALUE obj, VALUE protocol, VALUE port)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-23 09:47:26 +08:00
|
|
|
char *name;
|
|
|
|
|
|
|
|
if ((name = sigar_net_services_name_get(sigar, NUM2UINT(protocol), NUM2UINT(port)))) {
|
|
|
|
return rb_str_new2(name);
|
|
|
|
}
|
|
|
|
else {
|
2007-09-24 07:49:29 +08:00
|
|
|
return Qnil;
|
2007-09-23 09:47:26 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
static VALUE rb_cSigarCpuInfo;
|
|
|
|
|
2007-09-15 22:40:13 +08:00
|
|
|
static VALUE rb_sigar_cpu_info_list(VALUE obj)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-15 22:40:13 +08:00
|
|
|
int status;
|
|
|
|
sigar_cpu_info_list_t cpu_infos;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_cpu_info_list_get(sigar, &cpu_infos);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_list((char *)&cpu_infos.data[0],
|
|
|
|
cpu_infos.number,
|
|
|
|
sizeof(*cpu_infos.data),
|
|
|
|
rb_cSigarCpuInfo);
|
|
|
|
|
|
|
|
sigar_cpu_info_list_destroy(sigar, &cpu_infos);
|
|
|
|
|
|
|
|
return RETVAL;
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2008-09-14 08:17:44 +08:00
|
|
|
static VALUE rb_cSigarCpuPerc;
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
static VALUE rb_cSigarFileSystem;
|
|
|
|
|
|
|
|
static VALUE rb_sigar_file_system_list(VALUE obj)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
int status;
|
|
|
|
sigar_file_system_list_t fslist;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_file_system_list_get(sigar, &fslist);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_list((char *)&fslist.data[0],
|
|
|
|
fslist.number,
|
|
|
|
sizeof(*fslist.data),
|
|
|
|
rb_cSigarFileSystem);
|
|
|
|
|
|
|
|
sigar_file_system_list_destroy(sigar, &fslist);
|
|
|
|
|
|
|
|
return RETVAL;
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_cSigarWho;
|
|
|
|
|
2007-09-15 23:53:50 +08:00
|
|
|
static VALUE rb_sigar_who_list(VALUE obj)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-15 23:53:50 +08:00
|
|
|
int status;
|
|
|
|
sigar_who_list_t list;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_who_list_get(sigar, &list);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_list((char *)&list.data[0],
|
|
|
|
list.number,
|
|
|
|
sizeof(*list.data),
|
|
|
|
rb_cSigarWho);
|
|
|
|
|
|
|
|
sigar_who_list_destroy(sigar, &list);
|
|
|
|
|
|
|
|
return RETVAL;
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_cSigarNetRoute;
|
|
|
|
|
2007-09-24 11:21:29 +08:00
|
|
|
static VALUE rb_sigar_net_route_list(VALUE obj)
|
2007-09-03 08:49:22 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-24 11:21:29 +08:00
|
|
|
int status;
|
|
|
|
sigar_net_route_list_t list;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
|
|
|
status = sigar_net_route_list_get(sigar, &list);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_list((char *)&list.data[0],
|
|
|
|
list.number,
|
|
|
|
sizeof(*list.data),
|
|
|
|
rb_cSigarNetRoute);
|
|
|
|
|
|
|
|
sigar_net_route_list_destroy(sigar, &list);
|
|
|
|
|
|
|
|
return RETVAL;
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|
|
|
|
|
2009-03-16 14:20:45 +08:00
|
|
|
static VALUE rb_sigar_proc_list(int argc, VALUE *argv, VALUE obj)
|
2009-03-16 03:47:08 +08:00
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2009-03-16 03:47:08 +08:00
|
|
|
int status;
|
|
|
|
sigar_proc_list_t list;
|
|
|
|
VALUE RETVAL;
|
2009-03-16 14:20:45 +08:00
|
|
|
VALUE vptql;
|
2009-03-16 03:47:08 +08:00
|
|
|
|
2009-03-16 14:20:45 +08:00
|
|
|
rb_scan_args(argc, argv, "01", &vptql);
|
|
|
|
if (NIL_P(vptql)) {
|
|
|
|
status = sigar_proc_list_get(sigar, &list);
|
2009-03-16 03:47:08 +08:00
|
|
|
|
2009-03-16 14:20:45 +08:00
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
sigar_ptql_query_t *query;
|
|
|
|
sigar_ptql_error_t error;
|
|
|
|
char *ptql = StringValuePtr(vptql);
|
|
|
|
|
|
|
|
status = sigar_ptql_query_create(&query, ptql, &error);
|
|
|
|
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_RAISE(error.message);
|
|
|
|
}
|
2009-03-17 11:04:33 +08:00
|
|
|
sigar_ptql_re_impl_set(sigar, NULL, rbsigar_ptql_re_impl);
|
2009-03-16 14:20:45 +08:00
|
|
|
status = sigar_ptql_query_find(sigar, query, &list);
|
2009-03-17 11:04:33 +08:00
|
|
|
sigar_ptql_re_impl_set(sigar, NULL, NULL);
|
2009-03-16 14:20:45 +08:00
|
|
|
sigar_ptql_query_destroy(query);
|
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_RAISE(sigar_strerror(sigar, status));
|
|
|
|
}
|
2009-03-16 03:47:08 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_intlist(&list.data[0],
|
|
|
|
list.number);
|
|
|
|
|
|
|
|
sigar_proc_list_destroy(sigar, &list);
|
|
|
|
|
|
|
|
return RETVAL;
|
|
|
|
}
|
|
|
|
|
2007-09-16 05:03:11 +08:00
|
|
|
static VALUE rb_sigar_proc_args(VALUE obj, VALUE pid)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-16 05:03:11 +08:00
|
|
|
int status;
|
|
|
|
sigar_proc_args_t args;
|
|
|
|
VALUE RETVAL;
|
|
|
|
|
2009-03-16 03:33:54 +08:00
|
|
|
status = sigar_proc_args_get(sigar, OBJ2PID(pid), &args);
|
2007-09-16 05:29:11 +08:00
|
|
|
|
2007-09-16 05:03:11 +08:00
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
RETVAL = rb_sigar_new_strlist(args.data, args.number);
|
|
|
|
|
|
|
|
sigar_proc_args_destroy(sigar, &args);
|
|
|
|
|
|
|
|
return RETVAL;
|
|
|
|
}
|
|
|
|
|
2007-09-16 05:29:11 +08:00
|
|
|
static int rb_sigar_env_getall(void *data,
|
|
|
|
const char *key, int klen,
|
|
|
|
char *val, int vlen)
|
|
|
|
{
|
|
|
|
rb_hash_aset(*((VALUE*)data),
|
|
|
|
rb_str_new(key, klen),
|
|
|
|
rb_str_new(val, vlen));
|
|
|
|
return SIGAR_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_proc_env(VALUE obj, VALUE pid)
|
|
|
|
{
|
2009-07-29 13:38:38 +08:00
|
|
|
SIGAR_GET;
|
|
|
|
|
2007-09-16 05:29:11 +08:00
|
|
|
int status;
|
|
|
|
sigar_proc_env_t procenv;
|
|
|
|
VALUE RETVAL = rb_hash_new();
|
|
|
|
|
|
|
|
procenv.type = SIGAR_PROC_ENV_ALL;
|
|
|
|
procenv.env_getter = rb_sigar_env_getall;
|
|
|
|
procenv.data = &RETVAL;
|
|
|
|
|
2009-03-16 03:33:54 +08:00
|
|
|
status = sigar_proc_env_get(sigar, OBJ2PID(pid), &procenv);
|
2007-09-16 05:29:11 +08:00
|
|
|
if (status != SIGAR_OK) {
|
|
|
|
RB_SIGAR_CROAK;
|
|
|
|
}
|
|
|
|
|
|
|
|
return RETVAL;
|
|
|
|
}
|
|
|
|
|
2009-07-29 13:38:38 +08:00
|
|
|
VALUE rb = Qnil;
|
|
|
|
|
|
|
|
static const char *logger_consts[] = {
|
|
|
|
"FATAL", /* SIGAR_LOG_FATAL */
|
|
|
|
"ERROR", /* SIGAR_LOG_ERROR */
|
|
|
|
"WARN", /* SIGAR_LOG_WARN */
|
|
|
|
"INFO", /* SIGAR_LOG_INFO */
|
|
|
|
"DEBUG", /* SIGAR_LOG_DEBUG */
|
|
|
|
"DEBUG", /* SIGAR_LOG_TRACE */
|
|
|
|
};
|
|
|
|
|
|
|
|
static void rb_sigar_logger_impl(sigar_t *sigar, void *data,
|
|
|
|
int level, char *message)
|
|
|
|
{
|
|
|
|
rb_sigar_t *rbsigar = ((rb_sigar_t*)data);
|
|
|
|
VALUE logger = rbsigar->logger;
|
|
|
|
|
|
|
|
/* XXX: cost of this, better way? */
|
|
|
|
VALUE logger_const = rb_const_get(rb_cObject, rb_intern("Logger"));
|
|
|
|
VALUE logger_level = rb_const_get(logger_const,
|
|
|
|
rb_intern(logger_consts[level]));
|
|
|
|
VALUE msg = rb_str_new2(message);
|
|
|
|
|
|
|
|
rb_funcall(logger, rb_intern ("add"), 2, logger_level, msg);
|
|
|
|
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
static void rb_sigar_proc_impl(sigar_t *sigar, void *data,
|
|
|
|
int level, char *message)
|
|
|
|
{
|
|
|
|
rb_sigar_t *rbsigar = ((rb_sigar_t*)data);
|
|
|
|
VALUE logger = rbsigar->logger;
|
|
|
|
|
|
|
|
rb_funcall(logger, rb_intern("call"), 2, INT2FIX(level), rb_str_new2(message));
|
|
|
|
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_logger(VALUE obj)
|
|
|
|
{
|
|
|
|
rb_sigar_t *rbsigar = rb_sigar_get(obj);
|
|
|
|
|
|
|
|
return rbsigar->logger;
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_set_logger(VALUE obj, VALUE logger)
|
|
|
|
{
|
|
|
|
SIGAR_GET;
|
|
|
|
|
|
|
|
if (rb_obj_is_kind_of(logger, rb_cProc) ||
|
|
|
|
rb_respond_to(logger, rb_intern("call"))) {
|
|
|
|
|
|
|
|
sigar_log_impl_set(sigar, rbsigar, rb_sigar_proc_impl);
|
|
|
|
rbsigar->logger = logger;
|
|
|
|
|
|
|
|
return obj;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Have to load Logger to test for it properly */
|
|
|
|
rb_require("logger");
|
|
|
|
if (rb_obj_is_kind_of(logger, rb_path2class("Logger"))) {
|
|
|
|
sigar_log_impl_set(sigar, rbsigar, rb_sigar_logger_impl);
|
|
|
|
rbsigar->logger = logger;
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
rb_raise(rb_eArgError,
|
|
|
|
"value is not a proc object or subclass of Logger");
|
|
|
|
}
|
|
|
|
|
|
|
|
return obj;
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_log_level(VALUE obj)
|
|
|
|
{
|
|
|
|
SIGAR_GET;
|
|
|
|
|
|
|
|
return INT2FIX(sigar_log_level_get(sigar));
|
|
|
|
}
|
|
|
|
|
|
|
|
static VALUE rb_sigar_set_log_level(VALUE obj, VALUE level)
|
|
|
|
{
|
|
|
|
SIGAR_GET;
|
|
|
|
|
|
|
|
sigar_log_level_set(sigar, NUM2INT(level));
|
|
|
|
|
|
|
|
return obj;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
#include "./rbsigar_generated.rx"
|
|
|
|
|
2007-09-04 00:41:11 +08:00
|
|
|
#define RB_SIGAR_CONST_INT(name) \
|
|
|
|
rb_define_const(rclass, #name, INT2FIX(SIGAR_##name))
|
|
|
|
|
2009-07-19 07:26:19 +08:00
|
|
|
#define RB_SIGAR_DEFINE_CONST_STR(name, value) \
|
|
|
|
rb_define_const(rclass, name, rb_obj_freeze(rb_str_new2(value)))
|
|
|
|
|
2007-09-04 01:08:35 +08:00
|
|
|
#define RB_SIGAR_CONST_STR(name) \
|
|
|
|
rb_define_const(rclass, #name, rb_obj_freeze(rb_str_new2(SIGAR_##name)))
|
|
|
|
|
2007-09-04 00:41:11 +08:00
|
|
|
static void Init_rbsigar_constants(VALUE rclass)
|
|
|
|
{
|
|
|
|
RB_SIGAR_CONST_INT(IFF_UP);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_BROADCAST);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_DEBUG);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_LOOPBACK);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_POINTOPOINT);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_NOTRAILERS);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_RUNNING);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_NOARP);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_PROMISC);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_ALLMULTI);
|
|
|
|
RB_SIGAR_CONST_INT(IFF_MULTICAST);
|
2007-09-04 01:08:35 +08:00
|
|
|
|
2007-09-16 05:54:03 +08:00
|
|
|
RB_SIGAR_CONST_INT(NETCONN_CLIENT);
|
|
|
|
RB_SIGAR_CONST_INT(NETCONN_SERVER);
|
|
|
|
RB_SIGAR_CONST_INT(NETCONN_TCP);
|
|
|
|
RB_SIGAR_CONST_INT(NETCONN_UDP);
|
|
|
|
RB_SIGAR_CONST_INT(NETCONN_RAW);
|
|
|
|
RB_SIGAR_CONST_INT(NETCONN_UNIX);
|
|
|
|
|
2007-09-24 09:41:54 +08:00
|
|
|
RB_SIGAR_CONST_INT(TCP_ESTABLISHED);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_SYN_SENT);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_SYN_RECV);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_FIN_WAIT1);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_FIN_WAIT2);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_TIME_WAIT);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_CLOSE);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_CLOSE_WAIT);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_LAST_ACK);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_LISTEN);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_CLOSING);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_IDLE);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_BOUND);
|
|
|
|
RB_SIGAR_CONST_INT(TCP_UNKNOWN);
|
|
|
|
|
2009-06-30 08:20:19 +08:00
|
|
|
RB_SIGAR_CONST_INT(RTF_UP);
|
|
|
|
RB_SIGAR_CONST_INT(RTF_GATEWAY);
|
|
|
|
RB_SIGAR_CONST_INT(RTF_HOST);
|
|
|
|
|
2007-09-04 01:08:35 +08:00
|
|
|
RB_SIGAR_CONST_STR(NULL_HWADDR);
|
2009-07-29 13:38:38 +08:00
|
|
|
|
|
|
|
RB_SIGAR_CONST_INT(LOG_FATAL);
|
|
|
|
RB_SIGAR_CONST_INT(LOG_ERROR);
|
|
|
|
RB_SIGAR_CONST_INT(LOG_WARN);
|
|
|
|
RB_SIGAR_CONST_INT(LOG_INFO);
|
|
|
|
RB_SIGAR_CONST_INT(LOG_DEBUG);
|
|
|
|
RB_SIGAR_CONST_INT(LOG_TRACE);
|
2007-09-04 00:41:11 +08:00
|
|
|
}
|
|
|
|
|
2009-07-19 07:26:19 +08:00
|
|
|
static void Init_rbsigar_version(VALUE rclass)
|
|
|
|
{
|
|
|
|
sigar_version_t *sv = sigar_version_get();
|
|
|
|
RB_SIGAR_DEFINE_CONST_STR("BUILD_DATE", sv->build_date);
|
|
|
|
RB_SIGAR_DEFINE_CONST_STR("SCM_REVISION", sv->scm_revision);
|
|
|
|
RB_SIGAR_DEFINE_CONST_STR("VERSION", sv->version);
|
|
|
|
}
|
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
void Init_rbsigar(void)
|
|
|
|
{
|
2007-09-03 09:14:49 +08:00
|
|
|
VALUE rclass = rb_define_class("Sigar", rb_cObject);
|
2007-09-03 08:49:22 +08:00
|
|
|
|
2009-07-29 13:38:38 +08:00
|
|
|
rb_define_method(rclass, "logger", rb_sigar_logger, 0);
|
|
|
|
rb_define_method(rclass, "logger=", rb_sigar_set_logger, 1);
|
|
|
|
|
|
|
|
rb_define_method(rclass, "log_level", rb_sigar_log_level, 0);
|
|
|
|
rb_define_method(rclass, "log_level=", rb_sigar_set_log_level, 1);
|
|
|
|
|
2007-09-15 22:40:13 +08:00
|
|
|
rb_define_method(rclass, "cpu_info_list", rb_sigar_cpu_info_list, 0);
|
2007-09-03 08:49:22 +08:00
|
|
|
rb_define_method(rclass, "file_system_list", rb_sigar_file_system_list, 0);
|
2007-09-16 05:54:03 +08:00
|
|
|
rb_define_method(rclass, "net_connection_list", rb_sigar_net_connection_list, 1);
|
2007-09-03 10:42:41 +08:00
|
|
|
rb_define_method(rclass, "net_interface_list", rb_sigar_net_interface_list, 0);
|
2007-09-23 09:47:26 +08:00
|
|
|
rb_define_method(rclass, "net_services_name", rb_sigar_net_services_name, 2);
|
2007-09-24 07:48:29 +08:00
|
|
|
rb_define_method(rclass, "net_stat", rb_sigar_net_stat, 1);
|
2007-09-24 10:35:35 +08:00
|
|
|
rb_define_method(rclass, "net_stat_port", rb_sigar_net_stat_port, 3);
|
2007-09-24 11:21:29 +08:00
|
|
|
rb_define_method(rclass, "net_route_list", rb_sigar_net_route_list, 0);
|
2007-09-15 23:53:50 +08:00
|
|
|
rb_define_method(rclass, "who_list", rb_sigar_who_list, 0);
|
2009-03-16 14:20:45 +08:00
|
|
|
rb_define_method(rclass, "proc_list", rb_sigar_proc_list, -1);
|
2007-09-16 05:03:11 +08:00
|
|
|
rb_define_method(rclass, "proc_args", rb_sigar_proc_args, 1);
|
2007-09-16 05:29:11 +08:00
|
|
|
rb_define_method(rclass, "proc_env", rb_sigar_proc_env, 1);
|
2007-09-03 08:49:22 +08:00
|
|
|
|
|
|
|
rb_define_singleton_method(rclass, "new", rb_sigar_new, 0);
|
2007-09-03 09:57:02 +08:00
|
|
|
rb_define_singleton_method(rclass, "format_size", rb_sigar_format_size, 1);
|
2007-09-03 11:13:41 +08:00
|
|
|
rb_define_singleton_method(rclass, "net_interface_flags_to_s",
|
|
|
|
rb_sigar_net_interface_flags_to_s, 1);
|
2009-07-30 07:08:16 +08:00
|
|
|
rb_define_singleton_method(rclass, "net_scope_to_s",
|
|
|
|
rb_sigar_net_scope_to_s, 1);
|
2007-09-23 09:47:26 +08:00
|
|
|
rb_define_singleton_method(rclass, "net_connection_type_to_s",
|
|
|
|
rb_sigar_net_connection_type_to_s, 1);
|
|
|
|
rb_define_singleton_method(rclass, "net_connection_state_to_s",
|
|
|
|
rb_sigar_net_connection_state_to_s, 1);
|
2007-09-03 08:49:22 +08:00
|
|
|
|
2007-09-04 00:41:11 +08:00
|
|
|
Init_rbsigar_constants(rclass);
|
2009-07-19 07:26:19 +08:00
|
|
|
Init_rbsigar_version(rclass);
|
2007-09-04 00:41:11 +08:00
|
|
|
|
2007-09-03 08:49:22 +08:00
|
|
|
/* generated */
|
|
|
|
rb_sigar_define_module_methods(rclass);
|
2007-09-24 07:48:29 +08:00
|
|
|
rb_define_method(rb_cSigarNetStat, "tcp_states", rb_sigar_NetStat_tcp_states, 0);
|
2007-09-03 08:49:22 +08:00
|
|
|
}
|