Làm thế nào để sử dụng chương trình C để chạy lệnh trên thiết bị đầu cuối?


10

Tôi muốn tạo một chương trình bằng ngôn ngữ C cho phép tôi chạy một lệnh trong thiết bị đầu cuối.

Tôi đã tạo một chương trình trong shell script để cung cấp cho tôi ip của bất kỳ trang web nào được mở trong trình duyệt của tôi. Kịch bản shell này được thực thi bằng cách nhập lệnh này trong terminal:

sudo tcpdump -n dst port 80 -i eth

Giáo sư của tôi bảo tôi tạo một chương trình bằng ngôn ngữ C sẽ mở terminal và nhập lệnh này và sau đó tập lệnh shell của tôi sẽ hoạt động.

Xin vui lòng cho tôi biết làm thế nào để tạo ra một chương trình như vậy.

Câu trả lời:


8

bạn có thể sử dụng hàm system () có sẵn trong stdlib.h để chạy các lệnh.

SỰ MIÊU TẢ

system () thực thi một lệnh được chỉ định trong chuỗi bằng cách gọi / bin / sh -c chuỗi và trả về sau khi lệnh đã được hoàn thành. Trong quá trình thực thi lệnh, SIGCHLD sẽ bị chặn và SIGINT và SIGQUIT sẽ bị bỏ qua.

Bạn có thể đọc thêm về nó ở đây http://linux.about.com/l Library / cmd / blcmdl3_system.htmlm


Đây chắc chắn là một cách, nhưng có lẽ bạn không muốn chạy các lệnh từ chương trình ac, thay vào đó, hầu hết các chương trình Linux có một lib chỉ có thể mã trực tiếp của chương trình. Ví dụ ssh có thể sử dụng libssh . Thường có một lý do RẤT hạn chế để chạy các lệnh hệ thống từ mã. Nếu bạn đi nó rất nhiều, bạn gần như chắc chắn làm điều gì đó sai.
coteyr

Tôi đã thực hiện một chương trình ở C như thế này
Tehseen Malik

4

Xin chào tôi sẽ viết cho bạn một mã ví dụ, giải thích cho bạn và thực sự hy vọng điều này sẽ giúp bạn. nguyên mẫu của hàm là một cái gì đó như:

hệ thống int (const char * cmd);

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define MAX_CMN_LEN 100

int main(int argc, char *argv[])
{
    char cmd[MAX_CMN_LEN] = "", **p;

    if (argc < 2) /*no command specified*/
    {
        fprintf(stderr, "Usage: ./program_name terminal_command ...");
        exit(EXIT_FAILURE);
    }
    else
    {
        strcat(cmd, argv[1]);
        for (p = &argv[2]; *p; p++)
        {
            strcat(cmd, " ");
            strcat(cmd, *p);
        }
        system(cmd);
    }

    return 0;
}

1). mở một thiết bị đầu cuối và biên dịch chương trình

2). chạy nó (ví dụ trong Ubuntu) ./program_name comman_name -anything - mọi thứ

ví dụ: ./a.out miền địa phương -a

ví dụ này in tất cả các ngôn ngữ được hỗ trợ bởi trình biên dịch của tôi là gcc.

thêm thông tin:

p là một poniter để trỏ đến char (như argv là) p = & argv [2], trỏ đến chuỗi mọi thứ tôi gửi tất cả các chuỗi cho chuỗi cmd của tôi, tôi thoát khỏi vòng lặp khi * p trỏ tới NULL nhìn vào đây: -> tôi sẽ sử dụng biểu tượng này để nói các điểm tới (đừng nhầm nó với toán tử chọn mũi tên phải).

argv [0] -> chương trình tên

argv [1] -> command_name (trong ví dụ này tên lệnh sẽ là miền địa phương, nhưng hãy nhập lệnh bạn muốn kiểm tra thay thế)

argv [2] -> -tất cả mọi thứ (trong ví dụ này -a, đó là tất cả các địa phương)

argv [3] -> NULL (trong ví dụ này, điều này thoát khỏi vòng lặp)

ok đó là nó, tôi nghĩ.


Hãy chắc chắn rằng bạn không sử dụng điều này như một tập tin thực thi setuid, bởi vì nó có một khai thác tràn bộ đệm rõ ràng.
Martin

0

Tôi sẽ giả định rằng đây là về việc sử dụng nhị phân gốc setuid để thay thế sudo, thay vì chỉ thực thi lệnh tùy ý, vì vậy tôi sẽ đưa vào các phần khác của giải pháp.

Là một vấn đề bảo mật, chúng tôi tránh hệ thống () vì nó có thể bị tấn công.

Sau khi biên dịch, cài đặt nhị phân kết quả là setuid-root.

#include <unistd.h>
#inc loại <stdio.h>
#include <sysexits.h>

int chính (int argc, char ** argv) {
    if (argc> 2) {fputs ("quá nhiều args \ n", stderr); trả lại EX_USAGE; }
    if (argc> 1 && argv [1] [0] == '-') {fputs ("không có tùy chọn nào được phép \ n", stderr); trả lại EX_USAGE; }
    if (geteuid ()! = 0) {fputs ("không được cài đặt chính xác như setuid-root \ n", stderr); trả lại EX_UNAVAILABLE; }
    if (setuid (0) 1) p [6] = argv [1];

    / * Nếu mọi việc suôn sẻ, execv sẽ không trở lại
     * (vì chương trình này sẽ được thay thế bằng tcpdump) * /
    execv (p0, p);
    / * nếu chúng ta đến đây thì execv phải thất bại * /

    perror (p0);
    trả về EX_OSFILE;
}

nếu bạn đã lưu cái này dưới dạng foo.cvà muốn nó được cài đặt /usr/local/sbin/foo, hãy chạy:

tạo foo && cài đặt -o root -m 4511 foo / usr / local / sbin / foo
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.