62 lines
		
	
	
		
			1.1 KiB
		
	
	
	
		
			C++
		
	
	
	
			
		
		
	
	
			62 lines
		
	
	
		
			1.1 KiB
		
	
	
	
		
			C++
		
	
	
	
| #include "llvm/ADT/SmallString.h"
 | |
| #include "llvm/ADT/SmallVector.h"
 | |
| #include "llvm/Support/ManagedStatic.h"
 | |
| #include <cassert>
 | |
| #include <xlocale.h>
 | |
| 
 | |
| 
 | |
| namespace {
 | |
|   struct locale_holder {
 | |
|     locale_holder()
 | |
|     : l(newlocale(LC_CTYPE_MASK,"en_US.UTF-8",LC_GLOBAL_LOCALE))
 | |
|     {
 | |
|       assert(NULL!=l);
 | |
|     }
 | |
|     ~locale_holder() {
 | |
|       freelocale(l);
 | |
|     }
 | |
| 
 | |
|     int mbswidth(llvm::SmallString<16> s) const {
 | |
|        // this implementation assumes no '\0' in s
 | |
|       assert(s.size()==strlen(s.c_str()));
 | |
| 
 | |
|       size_t size = mbstowcs_l(NULL,s.c_str(),0,l);
 | |
|       assert(size!=(size_t)-1);
 | |
|       if (size==0)
 | |
|         return 0;
 | |
|       llvm::SmallVector<wchar_t,200> ws(size);
 | |
|       size = mbstowcs_l(&ws[0],s.c_str(),ws.size(),l);
 | |
|       assert(ws.size()==size);
 | |
|       return wcswidth_l(&ws[0],ws.size(),l);
 | |
|     }
 | |
| 
 | |
|     int isprint(int c) const {
 | |
|       return iswprint_l(c,l);
 | |
|     }
 | |
| 
 | |
|   private:
 | |
| 
 | |
|     locale_t l;
 | |
|   };
 | |
| 
 | |
|   llvm::ManagedStatic<locale_holder> l;
 | |
| }
 | |
| 
 | |
| namespace llvm {
 | |
| namespace sys {
 | |
| namespace locale {
 | |
| 
 | |
| int columnWidth(StringRef s) {
 | |
|   int width = l->mbswidth(s);
 | |
|   assert(width>=0);
 | |
|   return width;
 | |
| }
 | |
| 
 | |
| bool isPrint(int c) {
 | |
|   return l->isprint(c);
 | |
| }
 | |
| 
 | |
| }
 | |
| }
 | |
| }
 |