2013-07-29 64 views
0

我想用gtk_entry以「/ dev/mixer:line」或「/ dev/mixer:cd」的形式設置混音器設備。在調用strdup()之前指定值的空閒()字符strdup()

用戶必須以該格式混合器設備設置到條目:

/dev/mixer:line 

or: 

/dev/mixer:cd 

爲此,我編寫代碼來設置混頻器和具有的strdup()函數一樣的困境。 在調用strdup()之前釋放帶賦值的char()字符是錯誤的?

char *mixer_device = "/dev/mixer"; 
int mixer_channel = SOUND_MIXER_LINE; 
int fd = -1; 

int get_volume(void) 
{ 
    int v, cmd, devs; 
    int curvol = 0; 

    if(fd < 0) fd = open(mixer_device, O_RDONLY); 
    if(fd != -1) { 

      ioctl(fd, SOUND_MIXER_READ_DEVMASK, &devs); 
      if(devs & mixer_dev_mask) { 
        cmd = MIXER_READ(mixer_channel); 
      } else { 
        return curvol; 
      } 

      ioctl(fd, cmd, &v); 
      curvol = (v & 0xFF00) >> 8; 
    } 

    return curvol; 
} 

char *core_devnames[] = SOUND_DEVICE_NAMES; 

int set_device(const char *devname) 
{ 
    const char *channame; 
    int i; 

    /* if (mixer_device) free (mixer_device) <-- It is wrong ??? */ 
    mixer_device = strdup(devname); 
    if(!mixer_device) return -1; 

    i = strcspn(mixer_device, ":"); 
    if(i == strlen(mixer_device)) { 
      channame = "line"; 
    } else { 
      mixer_device[ i ] = 0; 
      channame = mixer_device + i + 1; 
    } 
    fd = open(mixer_device, O_RDONLY); 
    if(fd == 0) { 
      fprintf(stderr, "mixer: Can't open device %s, " 
        "mixer volume and mute unavailable.\n", mixer_device); 
      return -1; 
    } 

    return 0; 
} 

這是錯誤的與調用的strdup()

+3

調用'free'動態分配的內存是不確定的行爲。你在這裏設置初始值爲一個字符串文字:'char * mixer_device =「/ dev/mixer」;' –

回答

1

之前分配值free()的字符,您可能只調用free()如果指針指向的內存,將其與malloc()分配。在您的程序中,mixer_device最初指向一個文字字符串,因此調用free()會導致未定義的行爲。

而不是檢查mixer_device是否爲空,您需要另一個變量來跟蹤它是否指向初始文字字符串或使用strdup()創建的新字符串。或者,而不是將其指向一個字符串,你的啓動代碼可以做:

mixer_string = strdup("/dev/mixer"); 

所以它總是安全的釋放它。

0

您在此處設置的初始值:

char *mixer_device = "/dev/mixer"; 

它指向一個字符串,因此,如果您嘗試調用上mixer_devicefree你將有undefined behaviorfree只能叫上動態分配的內存,即從mallocstrdup等..一個解決方案是使用strdup來初始化變量:

mixer_device = strdup("/dev/mixer") ; 
0

初始化NUL升;

char *mixer_device = NULL; 

它是確定使用free(mixer_device)mixer_device的值爲NULL或,當然,通過malloc(), strdup(), realloc()賦值。 wHEN null,沒有任何東西被釋放,也沒有UB。然後,當過您要分配mixer_device,只需

free(mixer_device); 
mixer_device = strdup(NewName); 

在年底main(),執行非最終

free(mixer_device);