我尝试在 c 中锁定/解锁文件。如果文件存在,则没有问题,但如果文件不存在并且创建了文件,则文件保持锁定状态。如果我尝试打开该文件,它没有打开。它说“没有权限打开”。假设文件是:hey.txt,如果存在则没有问题我可以打开它。但如果 hey.txt 不存在,将创建文件并成功写入,但我无法打开该文件。当我将 sudo cat hey.txt 写入终端时,我只能看到文件内容
#define WRITE_FLAGS (O_WRONLY | O_CREAT | O_APPEND) //Write flag
int main(int argc , char* argv[]){
struct flock lock;
int fd=open(argv[0],WRITE_FLAGS);
int result_of_fcntl=0;
if(fd==-1){
perror("The file cannot opened.\n");
return-1;
}
memset(&lock,0,sizeof(lock));
lock.l_type=F_WRLCK;
result_of_fcntl=fcntl(fd,F_SETLKW,&lock);
char buffer2[]={"deneme\n"};
int byteswritten = write(fd,buffer2,7);
if(byteswritten==-1){
perror("Error while writing to file:");
return -1;
}
//unlock
lock.l_type=F_UNLCK;
result_of_fcntl=fcntl(fd,F_SETLKW,&lock);
if(result_of_fcntl==-1){
perror("Error:");
return -1;
}
int closeFlag= close(fd);
if(closeFlag==-1){
perror("The file cannot closed.\n");
return-1;
}
return 0;
}
Run Code Online (Sandbox Code Playgroud) 我想从程序集中调用类似 nanosleep 的东西,仅使用 SVC 调用。但仅使用我所拥有的有限信息,如何做到这一点并不明显,这个 macos 系统调用调用签名列表: https ://opensource.apple.com/source/xnu/xnu-1504.3.12/bsd/kern/syscalls 。掌握
我试图弄清楚 C 在调用 nanosleep 时做了什么,我能够将其简化为:
struct timespec { long tv_sec; long tv_nsec; };
int nanosleep(const struct timespec *__rqtp, struct timespec *__rmtp)
__asm("_" "nanosleep" );
int main() {
struct timespec remaining, request = { 3, 1 };
int response = nanosleep(&request, &remaining); }
Run Code Online (Sandbox Code Playgroud)
我不确定那__asm是做什么的,因为这看起来不像组装。不管怎样,我在苹果的 libc 源代码中找到了一个实现nanosleep。它依赖于对 while 的调用clock_get_time,而 libc 中未定义该调用。我在 XNU 源代码中发现了一个提及clock_get_time,但这是在 .defs 文件中,我不知道它是什么,而且似乎没有实现。
无论如何,是否有一些关于 SVC 调用的更好文档,或者我可以在某个地方找到 libc SVC 实现的程序集?
非常感谢任何信息或想法。
我正在使用一个简单的 C 程序,在其中使用 0664 创建文件时设置文件权限,open()然后将文件描述符传递到文件fdopen()并执行操作,然后将. 但令我惊讶的是,在程序完成执行后,我看到文件权限更改为0644。fwrite()fclose()
我的代码:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<fcntl.h>
int main (void)
{
int fd = -1;
FILE *fp = NULL;
fd = open("/tmp/myfile.cfg", O_WRONLY | O_CREAT | O_CLOEXEC, 0664);
fp = fdopen(fd, "w");
fclose(fp);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
为什么fd移交给后文件权限会被修改fdopen()?如何保留在通话中设置的权限open()?
我想知道使用数值系统调用是否有任何意义?
例如,取wait(4)或exit(3).我希望链接到这些的一些文档或解释.
int 0x80是一个系统调用,它在hexa中也是128.为什么内核使用int 0x80作为中断,当我声明int x时,他知道它只是一个名为x的整数,反之亦然?
在运行以下代码时:
#include <stdio.h>
#include <unistd.h>
static int x = 0;
int main(int argc, char *argv[])
{
pid_t p = getpid();
fork();
x++;
if (! fork()) {
x++;
if (fork()) {
x++;
}
}
printf("p%d: x = %d\n", getpid() - p, x);
sleep(60);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我得到以下输出:
p0: x = 1
p1: x = 1
p2: x = 3
p3: x = 3
p4: x = 2
p5: x = 2
Run Code Online (Sandbox Code Playgroud)
我不太明白这些值是如何以及在哪里增加的。的原始处理(P0)执行main()函数。第一个 fork() 创建一个 子进程 (p1)。然后,p0 和 p1 …
我有一个来自信息(mac os)的文件:
Created: Tuesday, 26 May 2020 at 11:21
Modified: 26 May 2021 at 15:40
Run Code Online (Sandbox Code Playgroud)
经过一些研究后我尝试这样做:
ctim := fi.Sys().(*syscall.Stat_t).Ctim
atim := fi.Sys().(*syscall.Stat_t).Atim
mtim := fi.Sys().(*syscall.Stat_t).Mtim
log.Println("ctim:", time.Unix(ctim.Sec, ctim.Nsec))
log.Println("atim:", time.Unix(atim.Sec, atim.Nsec))
log.Println("mtim:", time.Unix(mtim.Sec, mtim.Nsec))
Run Code Online (Sandbox Code Playgroud)
但他们都返回:
app_1 | 2021/05/26 15:40:17 ctim: 2021-05-26 15:40:17.199113879 +0000 UTC
app_1 | 2021/05/26 15:40:17 atim: 2021-05-26 15:40:16.457499729 +0000 UTC
app_1 | 2021/05/26 15:40:17 mtim: 2021-05-26 15:40:05.982391804 +0000 UTC
Run Code Online (Sandbox Code Playgroud)
另外,我正在使用 docker + docker-compose,golang:1.14-stretch在debian:bullseye-slim.
显然这不是文件的创建时间。知道我如何获得这些信息吗?
我有一个练习要做我需要用C编码的代码,相当于cat和nl的命令只使用系统调用.给我们的系统调用是open(),close(),read()和write().
我已经完成了"猫"等效,它似乎运行正常,现在我需要做"nl"一个,但我遇到麻烦,我将如何逐行编写.
我们的想法是使用尽可能少的系统调用.
我知道我需要在缓冲区找到'\n',我可以做一段时间循环缓冲区并找到'\n'位置(让我们称之为X)然后将X个字节写入stdout.
但循环遍历缓冲区中的所有字符搜索行的末尾对我来说感觉不对,但我不知道我怎么能这样做...
重要编辑:
我想你们中有些人错过了我的问题......我不需要解释如何做到这一点,这不是我的问题.我知道该怎么做(或者有一个非常好的主意,我还没有尝试过)."问题"是,它感觉不对遍历缓冲区,文件也好,都烧焦成炭,找到行的末尾(无论怎样).我不是说这不是答案,或者我不允许这样做,我只是在谈论我的想法.这似乎是一种奇怪的方式,这就是全部......但如果就是这样,那就是我的问题的答案.
我很欣赏每个人的帮助:)
我正在做一些x86练习; 我的任务让我write()在调试器中逐步调试库调用的汇编代码,直到我们达到SYSENTER指令,但是我得到的结果与我的一些同学不同.我看到的SYSENTER是:
?0xf7fdf421 <__kernel_vsyscall+1> push %edx
?0xf7fdf422 <__kernel_vsyscall+2> push %ebp
?0xf7fdf423 <__kernel_vsyscall+3> mov %esp,%ebp
?0xf7fdf425 <__kernel_vsyscall+5> sysenter
Run Code Online (Sandbox Code Playgroud)
这是我应该看到的吗?如果是这样,为什么它与我的一些同学看到的不一样?在执行sysenter指令之前,%edx和%ebp寄存器也保存在堆栈中吗?(根据我得到的答案,或者我错了,它似乎不是这样吗?)
这是我作业的原始说明:
汇编代码:
.file "A3Program2.c"
.section .rodata
.LC0:
.string "hello\n"
.LC1:
.string "xxxx\n"
.text
.globl secondCall
.type secondCall, @function
secondCall:
pushl %ebp
movl %esp, %ebp
subl $40, %esp
movl $6, 8(%esp)
movl $.LC0, 4(%esp)
movl $1, (%esp)
call write
movl %eax, -12(%ebp)
movl $8, 8(%esp)
movl $.LC1, 4(%esp)
movl $1, (%esp)
call write
addl %eax, …Run Code Online (Sandbox Code Playgroud) 根据我之前的一个问题Linux系统调用中的评论.Linux未在8086/88 Intel CPU上实现.那么第一款支持Linux并实现系统调用的英特尔CPU是什么?