Closed Kelvin-Ng closed 11 years ago
On 02/12/2013 10:05 AM, Kelvin Ng wrote:
Here is a great challenge that I want to try this with Linux kernel. It does not work well with it. It may because clang cannot compile the kernel properly.
For example, in fs/ext4/inode.c, in the function ext4_inode_csum, you can see that there is a line
csum_lo = raw->i_checksum_lo;
. It shows thatraw
has a member calledi_checksum_lo
. Unfortunately, the autocomplete does not showi_checksum_lo
.Looking at the declaration of
ext4_inode
, I found that there is really the memberi_checksum_lo
. Although there is a known issue that it does not support macro well, it is not in macro. What's wrong with this? (There are still some more examples)
This problem does not seem to be specific to clang_complete, but it is rather a generic clang completion problem.
Please enable g:clang_debug=1 and type ":mess" after having performed the completion. This will provide you with a command line that will allow you to reproduce the same completion with the clang binary. If this completion does not yield the expected result, please open a bug report in the clang bug database.
Tobias
@tobig It seems that this is some sort of gcc extension. Actually, the definition of ext4_inode is:
struct ext4_inode {
__le16 i_mode; /* File mode */
__le16 i_uid; /* Low 16 bits of Owner Uid */
__le32 i_size_lo; /* Size in bytes */
__le32 i_atime; /* Access time */
__le32 i_ctime; /* Inode Change time */
__le32 i_mtime; /* Modification time */
__le32 i_dtime; /* Deletion Time */
__le16 i_gid; /* Low 16 bits of Group Id */
__le16 i_links_count; /* Links count */
__le32 i_blocks_lo; /* Blocks count */
__le32 i_flags; /* File flags */
union {
struct {
__le32 l_i_version;
} linux1;
struct {
__u32 h_i_translator;
} hurd1;
struct {
__u32 m_i_reserved1;
} masix1;
} osd1; /* OS dependent 1 */
__le32 i_block[EXT4_N_BLOCKS];/* Pointers to blocks */
__le32 i_generation; /* File version (for NFS) */
__le32 i_file_acl_lo; /* File ACL */
__le32 i_size_high;
__le32 i_obso_faddr; /* Obsoleted fragment address */
union {
struct {
__le16 l_i_blocks_high; /* were l_i_reserved1 */
__le16 l_i_file_acl_high;
__le16 l_i_uid_high; /* these 2 fields */
__le16 l_i_gid_high; /* were reserved2[0] */
__le16 l_i_checksum_lo;/* crc32c(uuid+inum+inode) LE */
__le16 l_i_reserved;
} linux2;
struct {
__le16 h_i_reserved1; /* Obsoleted fragment number/size which are removed in ext4 */
__u16 h_i_mode_high;
__u16 h_i_uid_high;
__u16 h_i_gid_high;
__u32 h_i_author;
} hurd2;
struct {
__le16 h_i_reserved1; /* Obsoleted fragment number/size which are removed in ext4 */
__le16 m_i_file_acl_high;
__u32 m_i_reserved2[2];
} masix2;
} osd2; /* OS dependent 2 */
__le16 i_extra_isize;
__le16 i_checksum_hi; /* crc32c(uuid+inum+inode) BE */
__le32 i_ctime_extra; /* extra Change time (nsec << 2 | epoch) */
__le32 i_mtime_extra; /* extra Modification time(nsec << 2 | epoch) */
__le32 i_atime_extra; /* extra Access time (nsec << 2 | epoch) */
__le32 i_crtime; /* File Creation time */
__le32 i_crtime_extra; /* extra FileCreationtime (nsec << 2 | epoch) */
__le32 i_version_hi; /* high 32 bits for 64-bit version */
};
So, it is not normal that clang support it.
On 02/12/2013 10:45 AM, Kelvin Ng wrote:
@tobig It seems that this is some sort of gcc extension. Actually, the definition of ext4_inode is:
[..] A lot of code.
So, it is not normal that clang support it.
clang is certainly aiming at supporting the linux kernel. However, to report such bugs clang_complete is the wrong place. Please open a bug report with a minimal test case in the clang bug tracker. Chances are high that it gets fixed.
Tobi
@tobig
I actually don't know how gcc can support such kind of syntax so I don't know how to create a test case. Anyway, I will try to report this bug in a right place.
I think I have missed something... Here is a macro #define i_checksum_lo osd2.linux2.l_i_checksum_lo
so I understand what have happened (This is in #if defined(__KERNEL__) || defined(__linux__)
). I think clang should support such kind of thing, but the auto complete does not.
On 02/12/2013 10:53 AM, Kelvin Ng wrote:
I think I have missed something... Here is a macro
#define i_checksum_lo osd2.linux2.l_i_checksum_lo
so I understand what have happened. I think clang should support such kind of thing, but the auto complete does not.
Can you provide a minimal test case?
Tobi
@tobig
Here is a test case:
/* In test.h */
#define sth2_1 sth2.sth1_in_sth2
struct test_struct
{
int sth1;
struct
{
int sth1_in_sth2;
int sth2_in_sth2;
} sth2;
};
/* In test.c */
#include "test.h"
#include <stdio.h>
int main()
{
struct test_struct test;
test.sth2_1 = 123;
printf("%d\n", test.sth2.sth1_in_sth2);
}
It works when compiling the above code with clang (program outputs '123') but sth2_1
does not appear when completing test
.
On 02/12/2013 11:07 AM, Kelvin Ng wrote:
Here is a test case:
/* In test.h */ #define sth2_1 sth2.sth1_in_sth2 struct test_struct { int sth1; struct { int sth1_in_sth2; int sth2_in_sth2; } sth2; }; /* In test.c */ #include "test.h" #include <stdio.h> int main() { struct test_struct test; test.sth2_1 = 123; printf("%d\n", test.sth2.sth1_in_sth2); }
If you set g:clang_complete_macros = 1 and press CTRL-C CTRL-U at some random point, clang proposes the strh2_1 macro for completion. However, it seems after 'test.' no macros are proposed. You can report this a bug to clang.
Tobias
@tobig
Sorry, I cannot get what you mean. You mean after setting g:clang_complete_macros = 1 and pressing CTRL-C CTRL-U at some random point, strh2_1 will show after 'test.'? I have tried it but it doesn't.
On 02/12/2013 11:31 AM, Kelvin Ng wrote:
@tobig
Sorry, I cannot get what you mean. You mean after setting g:clang_complete_macros = 1 and pressing CTRL-C CTRL-U at some random point, strh2_1 will show after 'test.'?
By setting g:clang_complete_macros in your .vimrc file, you can enable macro completion. When you now trigger code completion at an empty line, the completion results will contain strh2_1. However, this does not work after 'test.', which seems to be a bug in clang.
Tobi
@tobig
That's true. I will report the bug to clang. Thank you.
On 02/12/2013 11:35 AM, Kelvin Ng wrote:
@tobig
That's true. I will report the bug to clang. Thank you.
Feel free to copy me in the bug report.
Tobi
@tobig
Here it is: http://llvm.org/bugs/show_bug.cgi?id=15244
Sorry, what is the meaning of 'copy me in the bug report'?...
Closing this one as this is not related to clang_complete.
Here is a great challenge that I want to try this with Linux kernel. It does not work well with it. It may because clang cannot compile the kernel properly.
For example, in fs/ext4/inode.c, in the function ext4_inode_csum, you can see that there is a line
csum_lo = raw->i_checksum_lo;
. It shows thatraw
has a member calledi_checksum_lo
. Unfortunately, the autocomplete does not showi_checksum_lo
.Looking at the declaration of
ext4_inode
, I found that there is NO memberi_checksum_lo
. But the source code really usecsum_lo = raw->i_checksum_lo;
. What's wrong with this?